Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(105)

Side by Side Diff: cc/trees/layer_tree_host_unittest_animation_timelines.cc

Issue 1010663002: CC Animations: Redirect all compositor animation requests to AnimationHost. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@introduce
Patch Set: Rebase and fix conflicts (HasPotentiallyRunningTransformAnimation) Created 5 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « cc/trees/layer_tree_host_impl.cc ('k') | cc/trees/layer_tree_impl.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 // Copyright 2015 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/animation_host.h"
9 #include "cc/animation/animation_id_provider.h"
10 #include "cc/animation/animation_player.h"
11 #include "cc/animation/animation_timeline.h"
12 #include "cc/animation/layer_animation_controller.h"
13 #include "cc/animation/scroll_offset_animation_curve.h"
14 #include "cc/animation/timing_function.h"
15 #include "cc/base/time_util.h"
16 #include "cc/layers/layer.h"
17 #include "cc/layers/layer_impl.h"
18 #include "cc/test/animation_test_common.h"
19 #include "cc/test/fake_content_layer.h"
20 #include "cc/test/fake_content_layer_client.h"
21 #include "cc/test/layer_tree_test.h"
22 #include "cc/trees/layer_tree_impl.h"
23
24 namespace cc {
25 namespace {
26
27 class LayerTreeHostTimelinesTest : public LayerTreeTest {
28 public:
29 LayerTreeHostTimelinesTest()
30 : timeline_id_(AnimationIdProvider::NextTimelineId()),
31 player_id_(AnimationIdProvider::NextPlayerId()),
32 player_child_id_(AnimationIdProvider::NextPlayerId()) {
33 timeline_ = AnimationTimeline::Create(timeline_id_);
34 player_ = AnimationPlayer::Create(player_id_);
35 player_child_ = AnimationPlayer::Create(player_child_id_);
36
37 player_->set_layer_animation_delegate(this);
38 }
39
40 void InitializeSettings(LayerTreeSettings* settings) override {
41 settings->use_compositor_animation_timelines = true;
42 }
43
44 void SetupTree() override { LayerTreeTest::SetupTree(); }
45
46 void AttachPlayersToTimeline() {
47 layer_tree_host()->animation_host()->AddAnimationTimeline(timeline_.get());
48 timeline_->AttachPlayer(player_.get());
49 timeline_->AttachPlayer(player_child_.get());
50 }
51
52 protected:
53 scoped_refptr<AnimationTimeline> timeline_;
54 scoped_refptr<AnimationPlayer> player_;
55 scoped_refptr<AnimationPlayer> player_child_;
56
57 const int timeline_id_;
58 const int player_id_;
59 const int player_child_id_;
60 };
61
62 // Add a layer animation and confirm that
63 // LayerTreeHostImpl::UpdateAnimationState does get called.
64 // Evolved frome LayerTreeHostAnimationTestAddAnimation
65 class LayerTreeHostTimelinesTestAddAnimation
66 : public LayerTreeHostTimelinesTest {
67 public:
68 LayerTreeHostTimelinesTestAddAnimation()
69 : update_animation_state_was_called_(false) {}
70
71 void BeginTest() override {
72 AttachPlayersToTimeline();
73 player_->AttachLayer(layer_tree_host()->root_layer()->id());
74 PostAddInstantAnimationToMainThreadPlayer(player_.get());
75 }
76
77 void UpdateAnimationState(LayerTreeHostImpl* host_impl,
78 bool has_unfinished_animation) override {
79 EXPECT_FALSE(has_unfinished_animation);
80 update_animation_state_was_called_ = true;
81 }
82
83 void NotifyAnimationStarted(base::TimeTicks monotonic_time,
84 Animation::TargetProperty target_property,
85 int group) override {
86 EXPECT_LT(base::TimeTicks(), monotonic_time);
87
88 LayerAnimationController* controller =
89 player_->layer_animation_controller();
90 Animation* animation = controller->GetAnimation(Animation::OPACITY);
91 if (animation)
92 player_->RemoveAnimation(animation->id());
93
94 EndTest();
95 }
96
97 void AfterTest() override { EXPECT_TRUE(update_animation_state_was_called_); }
98
99 private:
100 bool update_animation_state_was_called_;
101 };
102
103 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostTimelinesTestAddAnimation);
104
105 // Add a layer animation to a layer, but continually fail to draw. Confirm that
106 // after a while, we do eventually force a draw.
107 // Evolved from LayerTreeHostAnimationTestCheckerboardDoesNotStarveDraws.
108 class LayerTreeHostTimelinesTestCheckerboardDoesNotStarveDraws
109 : public LayerTreeHostTimelinesTest {
110 public:
111 LayerTreeHostTimelinesTestCheckerboardDoesNotStarveDraws()
112 : started_animating_(false) {}
113
114 void BeginTest() override {
115 AttachPlayersToTimeline();
116 player_->AttachLayer(layer_tree_host()->root_layer()->id());
117 PostAddAnimationToMainThreadPlayer(player_.get());
118 }
119
120 void AnimateLayers(LayerTreeHostImpl* host_impl,
121 base::TimeTicks monotonic_time) override {
122 started_animating_ = true;
123 }
124
125 void DrawLayersOnThread(LayerTreeHostImpl* host_impl) override {
126 if (started_animating_)
127 EndTest();
128 }
129
130 DrawResult PrepareToDrawOnThread(LayerTreeHostImpl* host_impl,
131 LayerTreeHostImpl::FrameData* frame,
132 DrawResult draw_result) override {
133 return DRAW_ABORTED_CHECKERBOARD_ANIMATIONS;
134 }
135
136 void AfterTest() override {}
137
138 private:
139 bool started_animating_;
140 };
141
142 // Starvation can only be an issue with the MT compositor.
143 MULTI_THREAD_TEST_F(LayerTreeHostTimelinesTestCheckerboardDoesNotStarveDraws);
144
145 // Ensures that animations eventually get deleted.
146 // Evolved from LayerTreeHostAnimationTestAnimationsGetDeleted.
147 class LayerTreeHostTimelinesTestAnimationsGetDeleted
148 : public LayerTreeHostTimelinesTest {
149 public:
150 LayerTreeHostTimelinesTestAnimationsGetDeleted()
151 : started_animating_(false) {}
152
153 void BeginTest() override {
154 AttachPlayersToTimeline();
155 player_->AttachLayer(layer_tree_host()->root_layer()->id());
156 PostAddAnimationToMainThreadPlayer(player_.get());
157 }
158
159 void AnimateLayers(LayerTreeHostImpl* host_impl,
160 base::TimeTicks monotonic_time) override {
161 bool have_animations = !host_impl->animation_host()
162 ->animation_registrar()
163 ->active_animation_controllers_for_testing()
164 .empty();
165 if (!started_animating_ && have_animations) {
166 started_animating_ = true;
167 return;
168 }
169
170 if (started_animating_ && !have_animations)
171 EndTest();
172 }
173
174 void NotifyAnimationFinished(base::TimeTicks monotonic_time,
175 Animation::TargetProperty target_property,
176 int group) override {
177 // Animations on the impl-side controller only get deleted during a commit,
178 // so we need to schedule a commit.
179 layer_tree_host()->SetNeedsCommit();
180 }
181
182 void AfterTest() override {}
183
184 private:
185 bool started_animating_;
186 };
187
188 SINGLE_AND_MULTI_THREAD_TEST_F(LayerTreeHostTimelinesTestAnimationsGetDeleted);
189
190 // Ensure that an animation's timing function is respected.
191 // Evolved from LayerTreeHostAnimationTestAddAnimationWithTimingFunction.
192 class LayerTreeHostTimelinesTestAddAnimationWithTimingFunction
193 : public LayerTreeHostTimelinesTest {
194 public:
195 LayerTreeHostTimelinesTestAddAnimationWithTimingFunction() {}
196
197 void SetupTree() override {
198 LayerTreeHostTimelinesTest::SetupTree();
199 content_ = FakeContentLayer::Create(&client_);
200 content_->SetBounds(gfx::Size(4, 4));
201 layer_tree_host()->root_layer()->AddChild(content_);
202
203 AttachPlayersToTimeline();
204 player_child_->AttachLayer(content_->id());
205 }
206
207 void BeginTest() override {
208 PostAddAnimationToMainThreadPlayer(player_child_.get());
209 }
210
211 void AnimateLayers(LayerTreeHostImpl* host_impl,
212 base::TimeTicks monotonic_time) override {
213 scoped_refptr<AnimationTimeline> timeline_impl =
214 host_impl->animation_host()->GetTimelineById(timeline_id_);
215 scoped_refptr<AnimationPlayer> player_child_impl =
216 timeline_impl->GetPlayerById(player_child_id_);
217
218 LayerAnimationController* controller_impl =
219 player_child_impl->layer_animation_controller();
220 if (!controller_impl)
221 return;
222
223 Animation* animation = controller_impl->GetAnimation(Animation::OPACITY);
224 if (!animation)
225 return;
226
227 const FloatAnimationCurve* curve =
228 animation->curve()->ToFloatAnimationCurve();
229 float start_opacity = curve->GetValue(base::TimeDelta());
230 float end_opacity = curve->GetValue(curve->Duration());
231 float linearly_interpolated_opacity =
232 0.25f * end_opacity + 0.75f * start_opacity;
233 base::TimeDelta time = TimeUtil::Scale(curve->Duration(), 0.25f);
234 // If the linear timing function associated with this animation was not
235 // picked up, then the linearly interpolated opacity would be different
236 // because of the default ease timing function.
237 EXPECT_FLOAT_EQ(linearly_interpolated_opacity, curve->GetValue(time));
238
239 EndTest();
240 }
241
242 void AfterTest() override {}
243
244 FakeContentLayerClient client_;
245 scoped_refptr<FakeContentLayer> content_;
246 };
247
248 SINGLE_AND_MULTI_THREAD_TEST_F(
249 LayerTreeHostTimelinesTestAddAnimationWithTimingFunction);
250
251 // Ensures that main thread animations have their start times synchronized with
252 // impl thread animations.
253 // Evolved from LayerTreeHostAnimationTestSynchronizeAnimationStartTimes.
254 class LayerTreeHostTimelinesTestSynchronizeAnimationStartTimes
255 : public LayerTreeHostTimelinesTest {
256 public:
257 LayerTreeHostTimelinesTestSynchronizeAnimationStartTimes() {}
258
259 void SetupTree() override {
260 LayerTreeHostTimelinesTest::SetupTree();
261 content_ = FakeContentLayer::Create(&client_);
262 content_->SetBounds(gfx::Size(4, 4));
263
264 layer_tree_host()->root_layer()->AddChild(content_);
265
266 AttachPlayersToTimeline();
267 player_child_->set_layer_animation_delegate(this);
268 player_child_->AttachLayer(content_->id());
269 }
270
271 void BeginTest() override {
272 PostAddAnimationToMainThreadPlayer(player_child_.get());
273 }
274
275 void NotifyAnimationStarted(base::TimeTicks monotonic_time,
276 Animation::TargetProperty target_property,
277 int group) override {
278 LayerAnimationController* controller =
279 player_child_->layer_animation_controller();
280 Animation* animation = controller->GetAnimation(Animation::OPACITY);
281 main_start_time_ = animation->start_time();
282 controller->RemoveAnimation(animation->id());
283 EndTest();
284 }
285
286 void UpdateAnimationState(LayerTreeHostImpl* impl_host,
287 bool has_unfinished_animation) override {
288 scoped_refptr<AnimationTimeline> timeline_impl =
289 impl_host->animation_host()->GetTimelineById(timeline_id_);
290 scoped_refptr<AnimationPlayer> player_child_impl =
291 timeline_impl->GetPlayerById(player_child_id_);
292
293 LayerAnimationController* controller =
294 player_child_impl->layer_animation_controller();
295 Animation* animation = controller->GetAnimation(Animation::OPACITY);
296 if (!animation)
297 return;
298
299 impl_start_time_ = animation->start_time();
300 }
301
302 void AfterTest() override {
303 EXPECT_EQ(impl_start_time_, main_start_time_);
304 EXPECT_LT(base::TimeTicks(), impl_start_time_);
305 }
306
307 private:
308 base::TimeTicks main_start_time_;
309 base::TimeTicks impl_start_time_;
310 FakeContentLayerClient client_;
311 scoped_refptr<FakeContentLayer> content_;
312 };
313
314 SINGLE_AND_MULTI_THREAD_TEST_F(
315 LayerTreeHostTimelinesTestSynchronizeAnimationStartTimes);
316
317 // Ensures that notify animation finished is called.
318 // Evolved from LayerTreeHostAnimationTestAnimationFinishedEvents.
319 class LayerTreeHostTimelinesTestAnimationFinishedEvents
320 : public LayerTreeHostTimelinesTest {
321 public:
322 LayerTreeHostTimelinesTestAnimationFinishedEvents() {}
323
324 void BeginTest() override {
325 AttachPlayersToTimeline();
326 player_->AttachLayer(layer_tree_host()->root_layer()->id());
327 PostAddInstantAnimationToMainThreadPlayer(player_.get());
328 }
329
330 void NotifyAnimationFinished(base::TimeTicks monotonic_time,
331 Animation::TargetProperty target_property,
332 int group) override {
333 LayerAnimationController* controller =
334 player_->layer_animation_controller();
335 Animation* animation = controller->GetAnimation(Animation::OPACITY);
336 if (animation)
337 controller->RemoveAnimation(animation->id());
338 EndTest();
339 }
340
341 void AfterTest() override {}
342 };
343
344 SINGLE_AND_MULTI_THREAD_TEST_F(
345 LayerTreeHostTimelinesTestAnimationFinishedEvents);
346
347 // Ensures that when opacity is being animated, this value does not cause the
348 // subtree to be skipped.
349 // Evolved from LayerTreeHostAnimationTestDoNotSkipLayersWithAnimatedOpacity.
350 class LayerTreeHostTimelinesTestDoNotSkipLayersWithAnimatedOpacity
351 : public LayerTreeHostTimelinesTest {
352 public:
353 LayerTreeHostTimelinesTestDoNotSkipLayersWithAnimatedOpacity()
354 : update_check_layer_(FakeContentLayer::Create(&client_)) {}
355
356 void SetupTree() override {
357 update_check_layer_->SetOpacity(0.f);
358 layer_tree_host()->SetRootLayer(update_check_layer_);
359 LayerTreeHostTimelinesTest::SetupTree();
360
361 AttachPlayersToTimeline();
362 player_->AttachLayer(update_check_layer_->id());
363 }
364
365 void BeginTest() override {
366 PostAddAnimationToMainThreadPlayer(player_.get());
367 }
368
369 void DidActivateTreeOnThread(LayerTreeHostImpl* host_impl) override {
370 scoped_refptr<AnimationTimeline> timeline_impl =
371 host_impl->animation_host()->GetTimelineById(timeline_id_);
372 scoped_refptr<AnimationPlayer> player_impl =
373 timeline_impl->GetPlayerById(player_id_);
374
375 LayerAnimationController* controller_impl =
376 player_impl->layer_animation_controller();
377 Animation* animation_impl =
378 controller_impl->GetAnimation(Animation::OPACITY);
379 controller_impl->RemoveAnimation(animation_impl->id());
380 EndTest();
381 }
382
383 void AfterTest() override {
384 // Update() should have been called once, proving that the layer was not
385 // skipped.
386 EXPECT_EQ(1u, update_check_layer_->update_count());
387
388 // clear update_check_layer_ so LayerTreeHost dies.
389 update_check_layer_ = NULL;
390 }
391
392 private:
393 FakeContentLayerClient client_;
394 scoped_refptr<FakeContentLayer> update_check_layer_;
395 };
396
397 SINGLE_AND_MULTI_THREAD_TEST_F(
398 LayerTreeHostTimelinesTestDoNotSkipLayersWithAnimatedOpacity);
399
400 // Layers added to tree with existing active animations should have the
401 // animation correctly recognized.
402 // Evolved from LayerTreeHostAnimationTestLayerAddedWithAnimation.
403 class LayerTreeHostTimelinesTestLayerAddedWithAnimation
404 : public LayerTreeHostTimelinesTest {
405 public:
406 LayerTreeHostTimelinesTestLayerAddedWithAnimation() {}
407
408 void BeginTest() override { PostSetNeedsCommitToMainThread(); }
409
410 void DidCommit() override {
411 if (layer_tree_host()->source_frame_number() == 1) {
412 AttachPlayersToTimeline();
413
414 scoped_refptr<Layer> layer = Layer::Create();
415 player_->AttachLayer(layer->id());
416 player_->set_layer_animation_delegate(this);
417
418 // Any valid AnimationCurve will do here.
419 scoped_ptr<AnimationCurve> curve(new FakeFloatAnimationCurve());
420 scoped_ptr<Animation> animation(
421 Animation::Create(curve.Pass(), 1, 1, Animation::OPACITY));
422 player_->AddAnimation(animation.Pass());
423
424 // We add the animation *before* attaching the layer to the tree.
425 layer_tree_host()->root_layer()->AddChild(layer);
426 }
427 }
428
429 void AnimateLayers(LayerTreeHostImpl* impl_host,
430 base::TimeTicks monotonic_time) override {
431 EndTest();
432 }
433
434 void AfterTest() override {}
435 };
436
437 SINGLE_AND_MULTI_THREAD_TEST_F(
438 LayerTreeHostTimelinesTestLayerAddedWithAnimation);
439
440 // Make sure the main thread can still execute animations when CanDraw() is not
441 // true.
442 // Evolved from LayerTreeHostAnimationTestRunAnimationWhenNotCanDraw
443 class LayerTreeHostTimelinesTestRunAnimationWhenNotCanDraw
444 : public LayerTreeHostTimelinesTest {
445 public:
446 LayerTreeHostTimelinesTestRunAnimationWhenNotCanDraw() : started_times_(0) {}
447
448 void SetupTree() override {
449 LayerTreeHostTimelinesTest::SetupTree();
450 content_ = FakeContentLayer::Create(&client_);
451 content_->SetBounds(gfx::Size(4, 4));
452 layer_tree_host()->root_layer()->AddChild(content_);
453
454 AttachPlayersToTimeline();
455 player_child_->AttachLayer(content_->id());
456 player_child_->set_layer_animation_delegate(this);
457 }
458
459 void BeginTest() override {
460 layer_tree_host()->SetViewportSize(gfx::Size());
461 PostAddAnimationToMainThreadPlayer(player_child_.get());
462 }
463
464 void NotifyAnimationStarted(base::TimeTicks monotonic_time,
465 Animation::TargetProperty target_property,
466 int group) override {
467 started_times_++;
468 }
469
470 void NotifyAnimationFinished(base::TimeTicks monotonic_time,
471 Animation::TargetProperty target_property,
472 int group) override {
473 EndTest();
474 }
475
476 void AfterTest() override { EXPECT_EQ(1, started_times_); }
477
478 private:
479 int started_times_;
480 FakeContentLayerClient client_;
481 scoped_refptr<FakeContentLayer> content_;
482 };
483
484 SINGLE_AND_MULTI_THREAD_TEST_F(
485 LayerTreeHostTimelinesTestRunAnimationWhenNotCanDraw);
486
487 // Animations should not be started when frames are being skipped due to
488 // checkerboard.
489 // Evolved from LayerTreeHostAnimationTestCheckerboardDoesntStartAnimations.
490 class LayerTreeHostTimelinesTestCheckerboardDoesntStartAnimations
491 : public LayerTreeHostTimelinesTest {
492 void SetupTree() override {
493 LayerTreeHostTimelinesTest::SetupTree();
494 content_ = FakeContentLayer::Create(&client_);
495 content_->SetBounds(gfx::Size(4, 4));
496 layer_tree_host()->root_layer()->AddChild(content_);
497
498 AttachPlayersToTimeline();
499 player_child_->AttachLayer(content_->id());
500 player_child_->set_layer_animation_delegate(this);
501 }
502
503 void InitializeSettings(LayerTreeSettings* settings) override {
504 // Make sure that drawing many times doesn't cause a checkerboarded
505 // animation to start so we avoid flake in this test.
506 settings->timeout_and_draw_when_animation_checkerboards = false;
507 LayerTreeHostTimelinesTest::InitializeSettings(settings);
508 }
509
510 void BeginTest() override {
511 prevented_draw_ = 0;
512 added_animations_ = 0;
513 started_times_ = 0;
514
515 PostSetNeedsCommitToMainThread();
516 }
517
518 DrawResult PrepareToDrawOnThread(LayerTreeHostImpl* host_impl,
519 LayerTreeHostImpl::FrameData* frame_data,
520 DrawResult draw_result) override {
521 if (added_animations_ < 2)
522 return draw_result;
523 if (TestEnded())
524 return draw_result;
525 // Act like there is checkerboard when the second animation wants to draw.
526 ++prevented_draw_;
527 if (prevented_draw_ > 2)
528 EndTest();
529 return DRAW_ABORTED_CHECKERBOARD_ANIMATIONS;
530 }
531
532 void DidCommitAndDrawFrame() override {
533 switch (layer_tree_host()->source_frame_number()) {
534 case 1:
535 // The animation is longer than 1 BeginFrame interval.
536 AddOpacityTransitionToPlayer(player_child_.get(), 0.1, 0.2f, 0.8f,
537 false);
538 added_animations_++;
539 break;
540 case 2:
541 // This second animation will not be drawn so it should not start.
542 AddAnimatedTransformToPlayer(player_child_.get(), 0.1, 5, 5);
543 added_animations_++;
544 break;
545 }
546 }
547
548 void NotifyAnimationStarted(base::TimeTicks monotonic_time,
549 Animation::TargetProperty target_property,
550 int group) override {
551 if (TestEnded())
552 return;
553 started_times_++;
554 }
555
556 void AfterTest() override {
557 // Make sure we tried to draw the second animation but failed.
558 EXPECT_LT(0, prevented_draw_);
559 // The first animation should be started, but the second should not because
560 // of checkerboard.
561 EXPECT_EQ(1, started_times_);
562 }
563
564 int prevented_draw_;
565 int added_animations_;
566 int started_times_;
567 FakeContentLayerClient client_;
568 scoped_refptr<FakeContentLayer> content_;
569 };
570
571 MULTI_THREAD_TEST_F(
572 LayerTreeHostTimelinesTestCheckerboardDoesntStartAnimations);
573
574 // When animations are simultaneously added to an existing layer and to a new
575 // layer, they should start at the same time, even when there's already a
576 // running animation on the existing layer.
577 // Evolved from LayerTreeHostAnimationTestAnimationsAddedToNewAndExistingLayers.
578 class LayerTreeHostTimelinesTestAnimationsAddedToNewAndExistingLayers
579 : public LayerTreeHostTimelinesTest {
580 public:
581 LayerTreeHostTimelinesTestAnimationsAddedToNewAndExistingLayers()
582 : frame_count_with_pending_tree_(0) {}
583
584 void BeginTest() override {
585 AttachPlayersToTimeline();
586 PostSetNeedsCommitToMainThread();
587 }
588
589 void DidCommit() override {
590 if (layer_tree_host()->source_frame_number() == 1) {
591 player_->AttachLayer(layer_tree_host()->root_layer()->id());
592 AddAnimatedTransformToPlayer(player_.get(), 4, 1, 1);
593 } else if (layer_tree_host()->source_frame_number() == 2) {
594 AddOpacityTransitionToPlayer(player_.get(), 1, 0.f, 0.5f, true);
595
596 scoped_refptr<Layer> layer = Layer::Create();
597 layer_tree_host()->root_layer()->AddChild(layer);
598 layer->SetBounds(gfx::Size(4, 4));
599
600 player_child_->AttachLayer(layer->id());
601 player_child_->set_layer_animation_delegate(this);
602 AddOpacityTransitionToPlayer(player_child_.get(), 1, 0.f, 0.5f, true);
603 }
604 }
605
606 void BeginCommitOnThread(LayerTreeHostImpl* host_impl) override {
607 if (host_impl->settings().impl_side_painting)
608 host_impl->BlockNotifyReadyToActivateForTesting(true);
609 }
610
611 void CommitCompleteOnThread(LayerTreeHostImpl* host_impl) override {
612 // For the commit that added animations to new and existing layers, keep
613 // blocking activation. We want to verify that even with activation blocked,
614 // the animation on the layer that's already in the active tree won't get a
615 // head start.
616 if (host_impl->settings().impl_side_painting &&
617 host_impl->pending_tree()->source_frame_number() != 2) {
618 host_impl->BlockNotifyReadyToActivateForTesting(false);
619 }
620 }
621
622 void WillBeginImplFrameOnThread(LayerTreeHostImpl* host_impl,
623 const BeginFrameArgs& args) override {
624 if (!host_impl->pending_tree() ||
625 host_impl->pending_tree()->source_frame_number() != 2)
626 return;
627
628 frame_count_with_pending_tree_++;
629 if (frame_count_with_pending_tree_ == 2 &&
630 host_impl->settings().impl_side_painting) {
631 host_impl->BlockNotifyReadyToActivateForTesting(false);
632 }
633 }
634
635 void UpdateAnimationState(LayerTreeHostImpl* host_impl,
636 bool has_unfinished_animation) override {
637 scoped_refptr<AnimationTimeline> timeline_impl =
638 host_impl->animation_host()->GetTimelineById(timeline_id_);
639 scoped_refptr<AnimationPlayer> player_impl =
640 timeline_impl->GetPlayerById(player_id_);
641 scoped_refptr<AnimationPlayer> player_child_impl =
642 timeline_impl->GetPlayerById(player_child_id_);
643
644 // wait for tree activation.
645 if (!player_impl->layer_animation_controller())
646 return;
647
648 LayerAnimationController* root_controller_impl =
649 player_impl->layer_animation_controller();
650 Animation* root_animation =
651 root_controller_impl->GetAnimation(Animation::OPACITY);
652 if (!root_animation || root_animation->run_state() != Animation::RUNNING)
653 return;
654
655 LayerAnimationController* child_controller_impl =
656 player_child_impl->layer_animation_controller();
657 Animation* child_animation =
658 child_controller_impl->GetAnimation(Animation::OPACITY);
659 EXPECT_EQ(Animation::RUNNING, child_animation->run_state());
660 EXPECT_EQ(root_animation->start_time(), child_animation->start_time());
661 root_controller_impl->AbortAnimations(Animation::OPACITY);
662 root_controller_impl->AbortAnimations(Animation::TRANSFORM);
663 child_controller_impl->AbortAnimations(Animation::OPACITY);
664 EndTest();
665 }
666
667 void AfterTest() override {}
668
669 private:
670 int frame_count_with_pending_tree_;
671 };
672
673 SINGLE_AND_MULTI_THREAD_BLOCKNOTIFY_TEST_F(
674 LayerTreeHostTimelinesTestAnimationsAddedToNewAndExistingLayers);
675
676 // Evolved from LayerTreeHostAnimationTestAddAnimationAfterAnimating.
677 class LayerTreeHostTimelinesTestAddAnimationAfterAnimating
678 : public LayerTreeHostTimelinesTest {
679 public:
680 LayerTreeHostTimelinesTestAddAnimationAfterAnimating()
681 : num_swap_buffers_(0) {}
682
683 void SetupTree() override {
684 LayerTreeHostTimelinesTest::SetupTree();
685 content_ = Layer::Create();
686 content_->SetBounds(gfx::Size(4, 4));
687 layer_tree_host()->root_layer()->AddChild(content_);
688
689 AttachPlayersToTimeline();
690
691 player_->AttachLayer(layer_tree_host()->root_layer()->id());
692 player_child_->AttachLayer(content_->id());
693 }
694
695 void BeginTest() override { PostSetNeedsCommitToMainThread(); }
696
697 void DidCommit() override {
698 switch (layer_tree_host()->source_frame_number()) {
699 case 1:
700 // First frame: add an animation to the root layer.
701 AddAnimatedTransformToPlayer(player_.get(), 0.1, 5, 5);
702 break;
703 case 2:
704 // Second frame: add an animation to the content layer. The root layer
705 // animation has caused us to animate already during this frame.
706 AddOpacityTransitionToPlayer(player_child_.get(), 0.1, 5, 5, false);
707 break;
708 }
709 }
710
711 void SwapBuffersOnThread(LayerTreeHostImpl* host_impl, bool result) override {
712 // After both animations have started, verify that they have valid
713 // start times.
714 num_swap_buffers_++;
715 AnimationRegistrar::AnimationControllerMap controllers_copy =
716 host_impl->animation_host()
717 ->animation_registrar()
718 ->active_animation_controllers_for_testing();
719 if (controllers_copy.size() == 2u) {
720 EndTest();
721 EXPECT_GE(num_swap_buffers_, 3);
722 for (auto& it : controllers_copy) {
723 int id = it.first;
724 if (id == host_impl->RootLayer()->id()) {
725 Animation* anim = it.second->GetAnimation(Animation::TRANSFORM);
726 EXPECT_GT((anim->start_time() - base::TimeTicks()).InSecondsF(), 0);
727 } else if (id == host_impl->RootLayer()->children()[0]->id()) {
728 Animation* anim = it.second->GetAnimation(Animation::OPACITY);
729 EXPECT_GT((anim->start_time() - base::TimeTicks()).InSecondsF(), 0);
730 }
731 }
732 }
733 }
734
735 void AfterTest() override {}
736
737 private:
738 scoped_refptr<Layer> content_;
739 int num_swap_buffers_;
740 };
741
742 SINGLE_AND_MULTI_THREAD_TEST_F(
743 LayerTreeHostTimelinesTestAddAnimationAfterAnimating);
744
745 } // namespace
746 } // namespace cc
OLDNEW
« no previous file with comments | « cc/trees/layer_tree_host_impl.cc ('k') | cc/trees/layer_tree_impl.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698