| OLD | NEW |
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "cc/animation/element_animations.h" | 5 #include "cc/animation/element_animations.h" |
| 6 | 6 |
| 7 #include "cc/animation/animation_delegate.h" | 7 #include "cc/animation/animation_delegate.h" |
| 8 #include "cc/animation/animation_host.h" | 8 #include "cc/animation/animation_host.h" |
| 9 #include "cc/animation/animation_id_provider.h" | 9 #include "cc/animation/animation_id_provider.h" |
| 10 #include "cc/animation/animation_player.h" | 10 #include "cc/animation/animation_player.h" |
| 11 #include "cc/animation/animation_timeline.h" | 11 #include "cc/animation/animation_timeline.h" |
| 12 #include "cc/animation/keyframed_animation_curve.h" |
| 13 #include "cc/animation/scroll_offset_animation_curve.h" |
| 14 #include "cc/animation/transform_operations.h" |
| 12 #include "cc/test/animation_test_common.h" | 15 #include "cc/test/animation_test_common.h" |
| 13 #include "cc/test/animation_timelines_test_common.h" | 16 #include "cc/test/animation_timelines_test_common.h" |
| 17 #include "ui/gfx/geometry/box_f.h" |
| 14 | 18 |
| 15 namespace cc { | 19 namespace cc { |
| 16 namespace { | 20 namespace { |
| 17 | 21 |
| 22 using base::TimeDelta; |
| 23 using base::TimeTicks; |
| 24 |
| 25 static base::TimeTicks TicksFromSecondsF(double seconds) { |
| 26 return base::TimeTicks::FromInternalValue(seconds * |
| 27 base::Time::kMicrosecondsPerSecond); |
| 28 } |
| 29 |
| 30 // An ElementAnimations cannot be ticked at 0.0, since an animation |
| 31 // with start time 0.0 is treated as an animation whose start time has |
| 32 // not yet been set. |
| 33 const TimeTicks kInitialTickTime = TicksFromSecondsF(1.0); |
| 34 |
| 18 class ElementAnimationsTest : public AnimationTimelinesTest { | 35 class ElementAnimationsTest : public AnimationTimelinesTest { |
| 19 public: | 36 public: |
| 20 ElementAnimationsTest() {} | 37 ElementAnimationsTest() {} |
| 21 ~ElementAnimationsTest() override {} | 38 ~ElementAnimationsTest() override {} |
| 22 }; | 39 }; |
| 23 | 40 |
| 24 // See animation_player_unittest.cc for integration with AnimationPlayer. | 41 // See animation_player_unittest.cc for integration with AnimationPlayer. |
| 25 | 42 |
| 26 TEST_F(ElementAnimationsTest, AttachToLayerInActiveTree) { | 43 TEST_F(ElementAnimationsTest, AttachToLayerInActiveTree) { |
| 27 // Set up the layer which is in active tree for main thread and not | 44 // Set up the layer which is in active tree for main thread and not |
| (...skipping 167 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 195 element_animations_impl->players_list().head(); | 212 element_animations_impl->players_list().head(); |
| 196 node != element_animations_impl->players_list().end(); | 213 node != element_animations_impl->players_list().end(); |
| 197 node = node->next()) { | 214 node = node->next()) { |
| 198 const AnimationPlayer* player_impl = node->value(); | 215 const AnimationPlayer* player_impl = node->value(); |
| 199 EXPECT_TRUE(timeline_->GetPlayerById(player_impl->id())); | 216 EXPECT_TRUE(timeline_->GetPlayerById(player_impl->id())); |
| 200 ++list_size_after; | 217 ++list_size_after; |
| 201 } | 218 } |
| 202 EXPECT_EQ(2, list_size_after); | 219 EXPECT_EQ(2, list_size_after); |
| 203 } | 220 } |
| 204 | 221 |
| 222 TEST_F(ElementAnimationsTest, SyncNewAnimation) { |
| 223 auto animations_impl = ElementAnimations::Create(); |
| 224 animations_impl->set_needs_active_value_observations(true); |
| 225 |
| 226 auto animations = ElementAnimations::Create(); |
| 227 animations->set_needs_active_value_observations(true); |
| 228 |
| 229 EXPECT_FALSE(animations_impl->GetAnimation(TargetProperty::OPACITY)); |
| 230 |
| 231 EXPECT_FALSE(animations->needs_to_start_animations_for_testing()); |
| 232 EXPECT_FALSE(animations_impl->needs_to_start_animations_for_testing()); |
| 233 |
| 234 int animation_id = |
| 235 AddOpacityTransitionToElementAnimations(animations.get(), 1, 0, 1, false); |
| 236 EXPECT_TRUE(animations->needs_to_start_animations_for_testing()); |
| 237 |
| 238 animations->PushPropertiesTo(animations_impl.get()); |
| 239 EXPECT_TRUE(animations_impl->needs_to_start_animations_for_testing()); |
| 240 animations_impl->ActivateAnimations(); |
| 241 |
| 242 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id)); |
| 243 EXPECT_EQ(Animation::WAITING_FOR_TARGET_AVAILABILITY, |
| 244 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 245 } |
| 246 |
| 247 TEST_F(ElementAnimationsTest, |
| 248 SyncScrollOffsetAnimationRespectsHasSetInitialValue) { |
| 249 CreateTestLayer(true, false); |
| 250 AttachTimelinePlayerLayer(); |
| 251 CreateImplTimelineAndPlayer(); |
| 252 |
| 253 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 254 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 255 |
| 256 EXPECT_FALSE(animations_impl->GetAnimation(TargetProperty::SCROLL_OFFSET)); |
| 257 |
| 258 EXPECT_FALSE(animations->needs_to_start_animations_for_testing()); |
| 259 EXPECT_FALSE(animations_impl->needs_to_start_animations_for_testing()); |
| 260 |
| 261 gfx::ScrollOffset initial_value(100.f, 300.f); |
| 262 gfx::ScrollOffset provider_initial_value(150.f, 300.f); |
| 263 gfx::ScrollOffset target_value(300.f, 200.f); |
| 264 |
| 265 client_impl_.SetScrollOffsetForAnimation(provider_initial_value); |
| 266 |
| 267 // Animation with initial value set. |
| 268 std::unique_ptr<ScrollOffsetAnimationCurve> curve_fixed( |
| 269 ScrollOffsetAnimationCurve::Create(target_value, |
| 270 EaseInOutTimingFunction::Create())); |
| 271 curve_fixed->SetInitialValue(initial_value); |
| 272 const int animation1_id = 1; |
| 273 std::unique_ptr<Animation> animation_fixed(Animation::Create( |
| 274 std::move(curve_fixed), animation1_id, 0, TargetProperty::SCROLL_OFFSET)); |
| 275 animations->AddAnimation(std::move(animation_fixed)); |
| 276 animations->PushPropertiesTo(animations_impl.get()); |
| 277 EXPECT_VECTOR2DF_EQ(initial_value, |
| 278 animations_impl->GetAnimationById(animation1_id) |
| 279 ->curve() |
| 280 ->ToScrollOffsetAnimationCurve() |
| 281 ->GetValue(base::TimeDelta())); |
| 282 |
| 283 // Animation without initial value set. |
| 284 std::unique_ptr<ScrollOffsetAnimationCurve> curve( |
| 285 ScrollOffsetAnimationCurve::Create(target_value, |
| 286 EaseInOutTimingFunction::Create())); |
| 287 const int animation2_id = 2; |
| 288 std::unique_ptr<Animation> animation(Animation::Create( |
| 289 std::move(curve), animation2_id, 0, TargetProperty::SCROLL_OFFSET)); |
| 290 animations->AddAnimation(std::move(animation)); |
| 291 animations->PushPropertiesTo(animations_impl.get()); |
| 292 EXPECT_VECTOR2DF_EQ(provider_initial_value, |
| 293 animations_impl->GetAnimationById(animation2_id) |
| 294 ->curve() |
| 295 ->ToScrollOffsetAnimationCurve() |
| 296 ->GetValue(base::TimeDelta())); |
| 297 } |
| 298 |
| 299 // If an animation is started on the impl thread before it is ticked on the main |
| 300 // thread, we must be sure to respect the synchronized start time. |
| 301 TEST_F(ElementAnimationsTest, DoNotClobberStartTimes) { |
| 302 CreateTestLayer(true, false); |
| 303 AttachTimelinePlayerLayer(); |
| 304 CreateImplTimelineAndPlayer(); |
| 305 |
| 306 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 307 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 308 |
| 309 EXPECT_FALSE(animations_impl->GetAnimation(TargetProperty::OPACITY)); |
| 310 |
| 311 int animation_id = |
| 312 AddOpacityTransitionToElementAnimations(animations.get(), 1, 0, 1, false); |
| 313 |
| 314 animations->PushPropertiesTo(animations_impl.get()); |
| 315 animations_impl->ActivateAnimations(); |
| 316 |
| 317 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id)); |
| 318 EXPECT_EQ(Animation::WAITING_FOR_TARGET_AVAILABILITY, |
| 319 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 320 |
| 321 auto events = host_impl_->CreateEvents(); |
| 322 animations_impl->Animate(kInitialTickTime); |
| 323 animations_impl->UpdateState(true, events.get()); |
| 324 |
| 325 // Synchronize the start times. |
| 326 EXPECT_EQ(1u, events->events_.size()); |
| 327 animations->NotifyAnimationStarted(events->events_[0]); |
| 328 EXPECT_EQ(animations->GetAnimationById(animation_id)->start_time(), |
| 329 animations_impl->GetAnimationById(animation_id)->start_time()); |
| 330 |
| 331 // Start the animation on the main thread. Should not affect the start time. |
| 332 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 333 animations->UpdateState(true, nullptr); |
| 334 EXPECT_EQ(animations->GetAnimationById(animation_id)->start_time(), |
| 335 animations_impl->GetAnimationById(animation_id)->start_time()); |
| 336 } |
| 337 |
| 338 TEST_F(ElementAnimationsTest, UseSpecifiedStartTimes) { |
| 339 CreateTestLayer(true, false); |
| 340 AttachTimelinePlayerLayer(); |
| 341 CreateImplTimelineAndPlayer(); |
| 342 |
| 343 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 344 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 345 |
| 346 int animation_id = |
| 347 AddOpacityTransitionToElementAnimations(animations.get(), 1, 0, 1, false); |
| 348 |
| 349 const TimeTicks start_time = TicksFromSecondsF(123); |
| 350 animations->GetAnimation(TargetProperty::OPACITY)->set_start_time(start_time); |
| 351 |
| 352 animations->PushPropertiesTo(animations_impl.get()); |
| 353 animations_impl->ActivateAnimations(); |
| 354 |
| 355 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id)); |
| 356 EXPECT_EQ(Animation::WAITING_FOR_TARGET_AVAILABILITY, |
| 357 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 358 |
| 359 auto events = host_impl_->CreateEvents(); |
| 360 animations_impl->Animate(kInitialTickTime); |
| 361 animations_impl->UpdateState(true, events.get()); |
| 362 |
| 363 // Synchronize the start times. |
| 364 EXPECT_EQ(1u, events->events_.size()); |
| 365 animations->NotifyAnimationStarted(events->events_[0]); |
| 366 |
| 367 EXPECT_EQ(start_time, |
| 368 animations->GetAnimationById(animation_id)->start_time()); |
| 369 EXPECT_EQ(animations->GetAnimationById(animation_id)->start_time(), |
| 370 animations_impl->GetAnimationById(animation_id)->start_time()); |
| 371 |
| 372 // Start the animation on the main thread. Should not affect the start time. |
| 373 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 374 animations->UpdateState(true, nullptr); |
| 375 EXPECT_EQ(start_time, |
| 376 animations->GetAnimationById(animation_id)->start_time()); |
| 377 EXPECT_EQ(animations->GetAnimationById(animation_id)->start_time(), |
| 378 animations_impl->GetAnimationById(animation_id)->start_time()); |
| 379 } |
| 380 |
| 381 // Tests that animationss activate and deactivate as expected. |
| 382 TEST_F(ElementAnimationsTest, Activation) { |
| 383 CreateTestLayer(true, false); |
| 384 AttachTimelinePlayerLayer(); |
| 385 CreateImplTimelineAndPlayer(); |
| 386 |
| 387 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 388 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 389 |
| 390 AnimationHost* host = client_.host(); |
| 391 AnimationHost* host_impl = client_impl_.host(); |
| 392 |
| 393 auto events = host_impl_->CreateEvents(); |
| 394 |
| 395 EXPECT_EQ(1u, host->all_element_animations_for_testing().size()); |
| 396 EXPECT_EQ(1u, host_impl->all_element_animations_for_testing().size()); |
| 397 |
| 398 // Initially, both animationss should be inactive. |
| 399 EXPECT_EQ(0u, host->active_element_animations_for_testing().size()); |
| 400 EXPECT_EQ(0u, host_impl->active_element_animations_for_testing().size()); |
| 401 |
| 402 AddOpacityTransitionToElementAnimations(animations.get(), 1, 0, 1, false); |
| 403 // The main thread animations should now be active. |
| 404 EXPECT_EQ(1u, host->active_element_animations_for_testing().size()); |
| 405 |
| 406 animations->PushPropertiesTo(animations_impl.get()); |
| 407 animations_impl->ActivateAnimations(); |
| 408 // Both animationss should now be active. |
| 409 EXPECT_EQ(1u, host->active_element_animations_for_testing().size()); |
| 410 EXPECT_EQ(1u, host_impl->active_element_animations_for_testing().size()); |
| 411 |
| 412 animations_impl->Animate(kInitialTickTime); |
| 413 animations_impl->UpdateState(true, events.get()); |
| 414 EXPECT_EQ(1u, events->events_.size()); |
| 415 animations->NotifyAnimationStarted(events->events_[0]); |
| 416 |
| 417 EXPECT_EQ(1u, host->active_element_animations_for_testing().size()); |
| 418 EXPECT_EQ(1u, host_impl->active_element_animations_for_testing().size()); |
| 419 |
| 420 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 421 animations->UpdateState(true, nullptr); |
| 422 EXPECT_EQ(1u, host->active_element_animations_for_testing().size()); |
| 423 |
| 424 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 425 animations->UpdateState(true, nullptr); |
| 426 EXPECT_EQ(Animation::FINISHED, |
| 427 animations->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 428 EXPECT_EQ(1u, host->active_element_animations_for_testing().size()); |
| 429 |
| 430 events = host_impl_->CreateEvents(); |
| 431 |
| 432 animations_impl->Animate(kInitialTickTime + |
| 433 TimeDelta::FromMilliseconds(1500)); |
| 434 animations_impl->UpdateState(true, events.get()); |
| 435 |
| 436 EXPECT_EQ( |
| 437 Animation::WAITING_FOR_DELETION, |
| 438 animations_impl->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 439 // The impl thread animations should have de-activated. |
| 440 EXPECT_EQ(0u, host_impl->active_element_animations_for_testing().size()); |
| 441 |
| 442 EXPECT_EQ(1u, events->events_.size()); |
| 443 animations->NotifyAnimationFinished(events->events_[0]); |
| 444 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1500)); |
| 445 animations->UpdateState(true, nullptr); |
| 446 |
| 447 EXPECT_EQ(Animation::WAITING_FOR_DELETION, |
| 448 animations->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 449 // The main thread animations should have de-activated. |
| 450 EXPECT_EQ(0u, host->active_element_animations_for_testing().size()); |
| 451 |
| 452 animations->PushPropertiesTo(animations_impl.get()); |
| 453 animations_impl->ActivateAnimations(); |
| 454 EXPECT_FALSE(animations->has_any_animation()); |
| 455 EXPECT_FALSE(animations_impl->has_any_animation()); |
| 456 EXPECT_EQ(0u, host->active_element_animations_for_testing().size()); |
| 457 EXPECT_EQ(0u, host_impl->active_element_animations_for_testing().size()); |
| 458 } |
| 459 |
| 460 TEST_F(ElementAnimationsTest, SyncPause) { |
| 461 CreateTestLayer(true, false); |
| 462 AttachTimelinePlayerLayer(); |
| 463 CreateImplTimelineAndPlayer(); |
| 464 |
| 465 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 466 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 467 |
| 468 EXPECT_FALSE(animations_impl->GetAnimation(TargetProperty::OPACITY)); |
| 469 |
| 470 // Two steps, three ranges: [0-1) -> 0.2, [1-2) -> 0.3, [2-3] -> 0.4. |
| 471 const double duration = 3.0; |
| 472 const int animation_id = AddOpacityStepsToElementAnimations( |
| 473 animations.get(), duration, 0.2f, 0.4f, 2); |
| 474 |
| 475 // Set start offset to be at the beginning of the second range. |
| 476 animations->GetAnimationById(animation_id) |
| 477 ->set_time_offset(TimeDelta::FromSecondsD(1.01)); |
| 478 |
| 479 animations->PushPropertiesTo(animations_impl.get()); |
| 480 animations_impl->ActivateAnimations(); |
| 481 |
| 482 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id)); |
| 483 EXPECT_EQ(Animation::WAITING_FOR_TARGET_AVAILABILITY, |
| 484 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 485 |
| 486 TimeTicks time = kInitialTickTime; |
| 487 |
| 488 // Start the animations on each animations. |
| 489 auto events = host_impl_->CreateEvents(); |
| 490 animations_impl->Animate(time); |
| 491 animations_impl->UpdateState(true, events.get()); |
| 492 EXPECT_EQ(1u, events->events_.size()); |
| 493 |
| 494 animations->Animate(time); |
| 495 animations->UpdateState(true, nullptr); |
| 496 animations->NotifyAnimationStarted(events->events_[0]); |
| 497 |
| 498 EXPECT_EQ(Animation::RUNNING, |
| 499 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 500 EXPECT_EQ(Animation::RUNNING, |
| 501 animations->GetAnimationById(animation_id)->run_state()); |
| 502 |
| 503 EXPECT_EQ(0.3f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 504 EXPECT_EQ(0.3f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 505 |
| 506 EXPECT_EQ(kInitialTickTime, |
| 507 animations->GetAnimationById(animation_id)->start_time()); |
| 508 EXPECT_EQ(kInitialTickTime, |
| 509 animations_impl->GetAnimationById(animation_id)->start_time()); |
| 510 |
| 511 // Pause the animation at the middle of the second range so the offset |
| 512 // delays animation until the middle of the third range. |
| 513 animations->PauseAnimation(animation_id, TimeDelta::FromSecondsD(1.5)); |
| 514 EXPECT_EQ(Animation::PAUSED, |
| 515 animations->GetAnimationById(animation_id)->run_state()); |
| 516 |
| 517 // The pause run state change should make it to the impl thread animations. |
| 518 animations->PushPropertiesTo(animations_impl.get()); |
| 519 animations_impl->ActivateAnimations(); |
| 520 |
| 521 // Advance time so it stays within the first range. |
| 522 time += TimeDelta::FromMilliseconds(10); |
| 523 animations->Animate(time); |
| 524 animations_impl->Animate(time); |
| 525 |
| 526 EXPECT_EQ(Animation::PAUSED, |
| 527 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 528 |
| 529 // Opacity value doesn't depend on time if paused at specified time offset. |
| 530 EXPECT_EQ(0.4f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 531 EXPECT_EQ(0.4f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 532 } |
| 533 |
| 534 TEST_F(ElementAnimationsTest, DoNotSyncFinishedAnimation) { |
| 535 CreateTestLayer(true, false); |
| 536 AttachTimelinePlayerLayer(); |
| 537 CreateImplTimelineAndPlayer(); |
| 538 |
| 539 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 540 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 541 |
| 542 auto events = host_impl_->CreateEvents(); |
| 543 |
| 544 EXPECT_FALSE(animations_impl->GetAnimation(TargetProperty::OPACITY)); |
| 545 |
| 546 int animation_id = |
| 547 AddOpacityTransitionToElementAnimations(animations.get(), 1, 0, 1, false); |
| 548 |
| 549 animations->PushPropertiesTo(animations_impl.get()); |
| 550 animations_impl->ActivateAnimations(); |
| 551 |
| 552 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id)); |
| 553 EXPECT_EQ(Animation::WAITING_FOR_TARGET_AVAILABILITY, |
| 554 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 555 |
| 556 events = host_impl_->CreateEvents(); |
| 557 animations_impl->Animate(kInitialTickTime); |
| 558 animations_impl->UpdateState(true, events.get()); |
| 559 EXPECT_EQ(1u, events->events_.size()); |
| 560 EXPECT_EQ(AnimationEvent::STARTED, events->events_[0].type); |
| 561 |
| 562 // Notify main thread animations that the animation has started. |
| 563 animations->NotifyAnimationStarted(events->events_[0]); |
| 564 |
| 565 // Complete animation on impl thread. |
| 566 events = host_impl_->CreateEvents(); |
| 567 animations_impl->Animate(kInitialTickTime + TimeDelta::FromSeconds(1)); |
| 568 animations_impl->UpdateState(true, events.get()); |
| 569 EXPECT_EQ(1u, events->events_.size()); |
| 570 EXPECT_EQ(AnimationEvent::FINISHED, events->events_[0].type); |
| 571 |
| 572 animations->NotifyAnimationFinished(events->events_[0]); |
| 573 |
| 574 animations->Animate(kInitialTickTime + TimeDelta::FromSeconds(2)); |
| 575 animations->UpdateState(true, nullptr); |
| 576 |
| 577 animations->PushPropertiesTo(animations_impl.get()); |
| 578 animations_impl->ActivateAnimations(); |
| 579 EXPECT_FALSE(animations->GetAnimationById(animation_id)); |
| 580 EXPECT_FALSE(animations_impl->GetAnimationById(animation_id)); |
| 581 } |
| 582 |
| 583 // Ensure that a finished animation is eventually deleted by both the |
| 584 // main-thread and the impl-thread animationss. |
| 585 TEST_F(ElementAnimationsTest, AnimationsAreDeleted) { |
| 586 CreateTestLayer(true, false); |
| 587 AttachTimelinePlayerLayer(); |
| 588 CreateImplTimelineAndPlayer(); |
| 589 |
| 590 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 591 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 592 |
| 593 auto events = host_impl_->CreateEvents(); |
| 594 |
| 595 AddOpacityTransitionToElementAnimations(animations.get(), 1.0, 0.0f, 1.0f, |
| 596 false); |
| 597 animations->Animate(kInitialTickTime); |
| 598 animations->UpdateState(true, nullptr); |
| 599 animations->PushPropertiesTo(animations_impl.get()); |
| 600 animations_impl->ActivateAnimations(); |
| 601 |
| 602 animations_impl->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 603 animations_impl->UpdateState(true, events.get()); |
| 604 |
| 605 // There should be a STARTED event for the animation. |
| 606 EXPECT_EQ(1u, events->events_.size()); |
| 607 EXPECT_EQ(AnimationEvent::STARTED, events->events_[0].type); |
| 608 animations->NotifyAnimationStarted(events->events_[0]); |
| 609 |
| 610 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 611 animations->UpdateState(true, nullptr); |
| 612 |
| 613 EXPECT_FALSE(host_->animation_waiting_for_deletion()); |
| 614 EXPECT_FALSE(host_impl_->animation_waiting_for_deletion()); |
| 615 |
| 616 events = host_impl_->CreateEvents(); |
| 617 animations_impl->Animate(kInitialTickTime + |
| 618 TimeDelta::FromMilliseconds(2000)); |
| 619 animations_impl->UpdateState(true, events.get()); |
| 620 |
| 621 EXPECT_TRUE(host_impl_->animation_waiting_for_deletion()); |
| 622 |
| 623 // There should be a FINISHED event for the animation. |
| 624 EXPECT_EQ(1u, events->events_.size()); |
| 625 EXPECT_EQ(AnimationEvent::FINISHED, events->events_[0].type); |
| 626 |
| 627 // Neither animations should have deleted the animation yet. |
| 628 EXPECT_TRUE(animations->GetAnimation(TargetProperty::OPACITY)); |
| 629 EXPECT_TRUE(animations_impl->GetAnimation(TargetProperty::OPACITY)); |
| 630 |
| 631 animations->NotifyAnimationFinished(events->events_[0]); |
| 632 |
| 633 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(3000)); |
| 634 animations->UpdateState(true, nullptr); |
| 635 EXPECT_TRUE(host_->animation_waiting_for_deletion()); |
| 636 |
| 637 animations->PushPropertiesTo(animations_impl.get()); |
| 638 |
| 639 // Both animationss should now have deleted the animation. The impl animations |
| 640 // should have deleted the animation even though activation has not occurred, |
| 641 // since the animation was already waiting for deletion when |
| 642 // PushPropertiesTo was called. |
| 643 EXPECT_FALSE(animations->has_any_animation()); |
| 644 EXPECT_FALSE(animations_impl->has_any_animation()); |
| 645 } |
| 646 |
| 647 // Tests that transitioning opacity from 0 to 1 works as expected. |
| 648 |
| 649 static std::unique_ptr<Animation> CreateAnimation( |
| 650 std::unique_ptr<AnimationCurve> curve, |
| 651 int group_id, |
| 652 TargetProperty::Type property) { |
| 653 return Animation::Create(std::move(curve), 0, group_id, property); |
| 654 } |
| 655 |
| 656 static const AnimationEvent* GetMostRecentPropertyUpdateEvent( |
| 657 const AnimationEvents* events) { |
| 658 const AnimationEvent* event = 0; |
| 659 for (size_t i = 0; i < events->events_.size(); ++i) |
| 660 if (events->events_[i].type == AnimationEvent::PROPERTY_UPDATE) |
| 661 event = &events->events_[i]; |
| 662 |
| 663 return event; |
| 664 } |
| 665 |
| 666 TEST_F(ElementAnimationsTest, TrivialTransition) { |
| 667 CreateTestLayer(true, false); |
| 668 AttachTimelinePlayerLayer(); |
| 669 |
| 670 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 671 |
| 672 auto events = host_impl_->CreateEvents(); |
| 673 |
| 674 std::unique_ptr<Animation> to_add(CreateAnimation( |
| 675 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 676 1, TargetProperty::OPACITY)); |
| 677 |
| 678 EXPECT_FALSE(animations->needs_to_start_animations_for_testing()); |
| 679 animations->AddAnimation(std::move(to_add)); |
| 680 EXPECT_TRUE(animations->needs_to_start_animations_for_testing()); |
| 681 animations->Animate(kInitialTickTime); |
| 682 EXPECT_FALSE(animations->needs_to_start_animations_for_testing()); |
| 683 animations->UpdateState(true, events.get()); |
| 684 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 685 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 686 // A non-impl-only animation should not generate property updates. |
| 687 const AnimationEvent* event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 688 EXPECT_FALSE(event); |
| 689 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 690 animations->UpdateState(true, events.get()); |
| 691 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 692 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 693 event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 694 EXPECT_FALSE(event); |
| 695 } |
| 696 |
| 697 TEST_F(ElementAnimationsTest, TrivialTransitionOnImpl) { |
| 698 CreateTestLayer(true, false); |
| 699 AttachTimelinePlayerLayer(); |
| 700 CreateImplTimelineAndPlayer(); |
| 701 |
| 702 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 703 |
| 704 auto events = host_impl_->CreateEvents(); |
| 705 |
| 706 std::unique_ptr<Animation> to_add(CreateAnimation( |
| 707 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 708 1, TargetProperty::OPACITY)); |
| 709 to_add->set_is_impl_only(true); |
| 710 |
| 711 animations_impl->AddAnimation(std::move(to_add)); |
| 712 animations_impl->Animate(kInitialTickTime); |
| 713 animations_impl->UpdateState(true, events.get()); |
| 714 EXPECT_TRUE(animations_impl->HasActiveAnimation()); |
| 715 EXPECT_EQ(0.f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 716 EXPECT_EQ(1u, events->events_.size()); |
| 717 const AnimationEvent* start_opacity_event = |
| 718 GetMostRecentPropertyUpdateEvent(events.get()); |
| 719 EXPECT_EQ(0.f, start_opacity_event->opacity); |
| 720 |
| 721 animations_impl->Animate(kInitialTickTime + |
| 722 TimeDelta::FromMilliseconds(1000)); |
| 723 animations_impl->UpdateState(true, events.get()); |
| 724 EXPECT_EQ(1.f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 725 EXPECT_FALSE(animations_impl->HasActiveAnimation()); |
| 726 EXPECT_EQ(2u, events->events_.size()); |
| 727 const AnimationEvent* end_opacity_event = |
| 728 GetMostRecentPropertyUpdateEvent(events.get()); |
| 729 EXPECT_EQ(1.f, end_opacity_event->opacity); |
| 730 } |
| 731 |
| 732 TEST_F(ElementAnimationsTest, TrivialTransformOnImpl) { |
| 733 CreateTestLayer(true, false); |
| 734 AttachTimelinePlayerLayer(); |
| 735 CreateImplTimelineAndPlayer(); |
| 736 |
| 737 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 738 |
| 739 auto events = host_impl_->CreateEvents(); |
| 740 |
| 741 // Choose different values for x and y to avoid coincidental values in the |
| 742 // observed transforms. |
| 743 const float delta_x = 3; |
| 744 const float delta_y = 4; |
| 745 |
| 746 std::unique_ptr<KeyframedTransformAnimationCurve> curve( |
| 747 KeyframedTransformAnimationCurve::Create()); |
| 748 |
| 749 // Create simple TRANSFORM animation. |
| 750 TransformOperations operations; |
| 751 curve->AddKeyframe( |
| 752 TransformKeyframe::Create(base::TimeDelta(), operations, nullptr)); |
| 753 operations.AppendTranslate(delta_x, delta_y, 0); |
| 754 curve->AddKeyframe(TransformKeyframe::Create( |
| 755 base::TimeDelta::FromSecondsD(1.0), operations, nullptr)); |
| 756 |
| 757 std::unique_ptr<Animation> animation( |
| 758 Animation::Create(std::move(curve), 1, 0, TargetProperty::TRANSFORM)); |
| 759 animation->set_is_impl_only(true); |
| 760 animations_impl->AddAnimation(std::move(animation)); |
| 761 |
| 762 // Run animation. |
| 763 animations_impl->Animate(kInitialTickTime); |
| 764 animations_impl->UpdateState(true, events.get()); |
| 765 EXPECT_TRUE(animations_impl->HasActiveAnimation()); |
| 766 EXPECT_EQ(gfx::Transform(), |
| 767 client_impl_.GetTransform(layer_id_, LayerTreeType::ACTIVE)); |
| 768 EXPECT_EQ(1u, events->events_.size()); |
| 769 const AnimationEvent* start_transform_event = |
| 770 GetMostRecentPropertyUpdateEvent(events.get()); |
| 771 ASSERT_TRUE(start_transform_event); |
| 772 EXPECT_EQ(gfx::Transform(), start_transform_event->transform); |
| 773 EXPECT_TRUE(start_transform_event->is_impl_only); |
| 774 |
| 775 gfx::Transform expected_transform; |
| 776 expected_transform.Translate(delta_x, delta_y); |
| 777 |
| 778 animations_impl->Animate(kInitialTickTime + |
| 779 TimeDelta::FromMilliseconds(1000)); |
| 780 animations_impl->UpdateState(true, events.get()); |
| 781 EXPECT_EQ(expected_transform, |
| 782 client_impl_.GetTransform(layer_id_, LayerTreeType::ACTIVE)); |
| 783 EXPECT_FALSE(animations_impl->HasActiveAnimation()); |
| 784 EXPECT_EQ(2u, events->events_.size()); |
| 785 const AnimationEvent* end_transform_event = |
| 786 GetMostRecentPropertyUpdateEvent(events.get()); |
| 787 EXPECT_EQ(expected_transform, end_transform_event->transform); |
| 788 EXPECT_TRUE(end_transform_event->is_impl_only); |
| 789 } |
| 790 |
| 791 TEST_F(ElementAnimationsTest, FilterTransition) { |
| 792 CreateTestLayer(true, false); |
| 793 AttachTimelinePlayerLayer(); |
| 794 |
| 795 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 796 |
| 797 auto events = host_impl_->CreateEvents(); |
| 798 |
| 799 std::unique_ptr<KeyframedFilterAnimationCurve> curve( |
| 800 KeyframedFilterAnimationCurve::Create()); |
| 801 |
| 802 FilterOperations start_filters; |
| 803 start_filters.Append(FilterOperation::CreateBrightnessFilter(1.f)); |
| 804 curve->AddKeyframe( |
| 805 FilterKeyframe::Create(base::TimeDelta(), start_filters, nullptr)); |
| 806 FilterOperations end_filters; |
| 807 end_filters.Append(FilterOperation::CreateBrightnessFilter(2.f)); |
| 808 curve->AddKeyframe(FilterKeyframe::Create(base::TimeDelta::FromSecondsD(1.0), |
| 809 end_filters, nullptr)); |
| 810 |
| 811 std::unique_ptr<Animation> animation( |
| 812 Animation::Create(std::move(curve), 1, 0, TargetProperty::FILTER)); |
| 813 animations->AddAnimation(std::move(animation)); |
| 814 |
| 815 animations->Animate(kInitialTickTime); |
| 816 animations->UpdateState(true, events.get()); |
| 817 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 818 EXPECT_EQ(start_filters, |
| 819 client_.GetFilters(layer_id_, LayerTreeType::ACTIVE)); |
| 820 // A non-impl-only animation should not generate property updates. |
| 821 const AnimationEvent* event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 822 EXPECT_FALSE(event); |
| 823 |
| 824 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 825 animations->UpdateState(true, events.get()); |
| 826 EXPECT_EQ(1u, client_.GetFilters(layer_id_, LayerTreeType::ACTIVE).size()); |
| 827 EXPECT_EQ(FilterOperation::CreateBrightnessFilter(1.5f), |
| 828 client_.GetFilters(layer_id_, LayerTreeType::ACTIVE).at(0)); |
| 829 event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 830 EXPECT_FALSE(event); |
| 831 |
| 832 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 833 animations->UpdateState(true, events.get()); |
| 834 EXPECT_EQ(end_filters, client_.GetFilters(layer_id_, LayerTreeType::ACTIVE)); |
| 835 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 836 event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 837 EXPECT_FALSE(event); |
| 838 } |
| 839 |
| 840 TEST_F(ElementAnimationsTest, FilterTransitionOnImplOnly) { |
| 841 CreateTestLayer(true, false); |
| 842 AttachTimelinePlayerLayer(); |
| 843 CreateImplTimelineAndPlayer(); |
| 844 |
| 845 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 846 |
| 847 auto events = host_impl_->CreateEvents(); |
| 848 |
| 849 std::unique_ptr<KeyframedFilterAnimationCurve> curve( |
| 850 KeyframedFilterAnimationCurve::Create()); |
| 851 |
| 852 // Create simple FILTER animation. |
| 853 FilterOperations start_filters; |
| 854 start_filters.Append(FilterOperation::CreateBrightnessFilter(1.f)); |
| 855 curve->AddKeyframe( |
| 856 FilterKeyframe::Create(base::TimeDelta(), start_filters, nullptr)); |
| 857 FilterOperations end_filters; |
| 858 end_filters.Append(FilterOperation::CreateBrightnessFilter(2.f)); |
| 859 curve->AddKeyframe(FilterKeyframe::Create(base::TimeDelta::FromSecondsD(1.0), |
| 860 end_filters, nullptr)); |
| 861 |
| 862 std::unique_ptr<Animation> animation( |
| 863 Animation::Create(std::move(curve), 1, 0, TargetProperty::FILTER)); |
| 864 animation->set_is_impl_only(true); |
| 865 animations_impl->AddAnimation(std::move(animation)); |
| 866 |
| 867 // Run animation. |
| 868 animations_impl->Animate(kInitialTickTime); |
| 869 animations_impl->UpdateState(true, events.get()); |
| 870 EXPECT_TRUE(animations_impl->HasActiveAnimation()); |
| 871 EXPECT_EQ(start_filters, |
| 872 client_impl_.GetFilters(layer_id_, LayerTreeType::ACTIVE)); |
| 873 EXPECT_EQ(1u, events->events_.size()); |
| 874 const AnimationEvent* start_filter_event = |
| 875 GetMostRecentPropertyUpdateEvent(events.get()); |
| 876 EXPECT_TRUE(start_filter_event); |
| 877 EXPECT_EQ(start_filters, start_filter_event->filters); |
| 878 EXPECT_TRUE(start_filter_event->is_impl_only); |
| 879 |
| 880 animations_impl->Animate(kInitialTickTime + |
| 881 TimeDelta::FromMilliseconds(1000)); |
| 882 animations_impl->UpdateState(true, events.get()); |
| 883 EXPECT_EQ(end_filters, |
| 884 client_impl_.GetFilters(layer_id_, LayerTreeType::ACTIVE)); |
| 885 EXPECT_FALSE(animations_impl->HasActiveAnimation()); |
| 886 EXPECT_EQ(2u, events->events_.size()); |
| 887 const AnimationEvent* end_filter_event = |
| 888 GetMostRecentPropertyUpdateEvent(events.get()); |
| 889 EXPECT_TRUE(end_filter_event); |
| 890 EXPECT_EQ(end_filters, end_filter_event->filters); |
| 891 EXPECT_TRUE(end_filter_event->is_impl_only); |
| 892 } |
| 893 |
| 894 TEST_F(ElementAnimationsTest, ScrollOffsetTransition) { |
| 895 CreateTestLayer(true, false); |
| 896 AttachTimelinePlayerLayer(); |
| 897 CreateImplTimelineAndPlayer(); |
| 898 |
| 899 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 900 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 901 |
| 902 auto events = host_impl_->CreateEvents(); |
| 903 |
| 904 gfx::ScrollOffset initial_value(100.f, 300.f); |
| 905 gfx::ScrollOffset target_value(300.f, 200.f); |
| 906 std::unique_ptr<ScrollOffsetAnimationCurve> curve( |
| 907 ScrollOffsetAnimationCurve::Create(target_value, |
| 908 EaseInOutTimingFunction::Create())); |
| 909 |
| 910 std::unique_ptr<Animation> animation( |
| 911 Animation::Create(std::move(curve), 1, 0, TargetProperty::SCROLL_OFFSET)); |
| 912 animation->set_needs_synchronized_start_time(true); |
| 913 animations->AddAnimation(std::move(animation)); |
| 914 |
| 915 client_impl_.SetScrollOffsetForAnimation(initial_value); |
| 916 animations->PushPropertiesTo(animations_impl.get()); |
| 917 animations_impl->ActivateAnimations(); |
| 918 EXPECT_TRUE(animations_impl->GetAnimation(TargetProperty::SCROLL_OFFSET)); |
| 919 TimeDelta duration = |
| 920 animations_impl->GetAnimation(TargetProperty::SCROLL_OFFSET) |
| 921 ->curve() |
| 922 ->Duration(); |
| 923 EXPECT_EQ(duration, animations->GetAnimation(TargetProperty::SCROLL_OFFSET) |
| 924 ->curve() |
| 925 ->Duration()); |
| 926 |
| 927 animations->Animate(kInitialTickTime); |
| 928 animations->UpdateState(true, nullptr); |
| 929 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 930 EXPECT_EQ(initial_value, |
| 931 client_.GetScrollOffset(layer_id_, LayerTreeType::ACTIVE)); |
| 932 |
| 933 animations_impl->Animate(kInitialTickTime); |
| 934 animations_impl->UpdateState(true, events.get()); |
| 935 EXPECT_TRUE(animations_impl->HasActiveAnimation()); |
| 936 EXPECT_EQ(initial_value, |
| 937 client_impl_.GetScrollOffset(layer_id_, LayerTreeType::ACTIVE)); |
| 938 // Scroll offset animations should not generate property updates. |
| 939 const AnimationEvent* event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 940 EXPECT_FALSE(event); |
| 941 |
| 942 animations->NotifyAnimationStarted(events->events_[0]); |
| 943 animations->Animate(kInitialTickTime + duration / 2); |
| 944 animations->UpdateState(true, nullptr); |
| 945 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 946 EXPECT_VECTOR2DF_EQ( |
| 947 gfx::Vector2dF(200.f, 250.f), |
| 948 client_.GetScrollOffset(layer_id_, LayerTreeType::ACTIVE)); |
| 949 |
| 950 animations_impl->Animate(kInitialTickTime + duration / 2); |
| 951 animations_impl->UpdateState(true, events.get()); |
| 952 EXPECT_VECTOR2DF_EQ( |
| 953 gfx::Vector2dF(200.f, 250.f), |
| 954 client_impl_.GetScrollOffset(layer_id_, LayerTreeType::ACTIVE)); |
| 955 event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 956 EXPECT_FALSE(event); |
| 957 |
| 958 animations_impl->Animate(kInitialTickTime + duration); |
| 959 animations_impl->UpdateState(true, events.get()); |
| 960 EXPECT_VECTOR2DF_EQ(target_value, client_impl_.GetScrollOffset( |
| 961 layer_id_, LayerTreeType::ACTIVE)); |
| 962 EXPECT_FALSE(animations_impl->HasActiveAnimation()); |
| 963 event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 964 EXPECT_FALSE(event); |
| 965 |
| 966 animations->Animate(kInitialTickTime + duration); |
| 967 animations->UpdateState(true, nullptr); |
| 968 EXPECT_VECTOR2DF_EQ( |
| 969 target_value, client_.GetScrollOffset(layer_id_, LayerTreeType::ACTIVE)); |
| 970 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 971 } |
| 972 |
| 973 TEST_F(ElementAnimationsTest, ScrollOffsetTransitionOnImplOnly) { |
| 974 CreateTestLayer(true, false); |
| 975 AttachTimelinePlayerLayer(); |
| 976 CreateImplTimelineAndPlayer(); |
| 977 |
| 978 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 979 |
| 980 auto events = host_impl_->CreateEvents(); |
| 981 |
| 982 gfx::ScrollOffset initial_value(100.f, 300.f); |
| 983 gfx::ScrollOffset target_value(300.f, 200.f); |
| 984 std::unique_ptr<ScrollOffsetAnimationCurve> curve( |
| 985 ScrollOffsetAnimationCurve::Create(target_value, |
| 986 EaseInOutTimingFunction::Create())); |
| 987 curve->SetInitialValue(initial_value); |
| 988 double duration_in_seconds = curve->Duration().InSecondsF(); |
| 989 |
| 990 std::unique_ptr<Animation> animation( |
| 991 Animation::Create(std::move(curve), 1, 0, TargetProperty::SCROLL_OFFSET)); |
| 992 animation->set_is_impl_only(true); |
| 993 animations_impl->AddAnimation(std::move(animation)); |
| 994 |
| 995 animations_impl->Animate(kInitialTickTime); |
| 996 animations_impl->UpdateState(true, events.get()); |
| 997 EXPECT_TRUE(animations_impl->HasActiveAnimation()); |
| 998 EXPECT_EQ(initial_value, |
| 999 client_impl_.GetScrollOffset(layer_id_, LayerTreeType::ACTIVE)); |
| 1000 // Scroll offset animations should not generate property updates. |
| 1001 const AnimationEvent* event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 1002 EXPECT_FALSE(event); |
| 1003 |
| 1004 TimeDelta duration = TimeDelta::FromMicroseconds( |
| 1005 duration_in_seconds * base::Time::kMicrosecondsPerSecond); |
| 1006 |
| 1007 animations_impl->Animate(kInitialTickTime + duration / 2); |
| 1008 animations_impl->UpdateState(true, events.get()); |
| 1009 EXPECT_VECTOR2DF_EQ( |
| 1010 gfx::Vector2dF(200.f, 250.f), |
| 1011 client_impl_.GetScrollOffset(layer_id_, LayerTreeType::ACTIVE)); |
| 1012 event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 1013 EXPECT_FALSE(event); |
| 1014 |
| 1015 animations_impl->Animate(kInitialTickTime + duration); |
| 1016 animations_impl->UpdateState(true, events.get()); |
| 1017 EXPECT_VECTOR2DF_EQ(target_value, client_impl_.GetScrollOffset( |
| 1018 layer_id_, LayerTreeType::ACTIVE)); |
| 1019 EXPECT_FALSE(animations_impl->HasActiveAnimation()); |
| 1020 event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 1021 EXPECT_FALSE(event); |
| 1022 } |
| 1023 |
| 1024 // Ensure that when the impl animations doesn't have a value provider, |
| 1025 // the main-thread animations's value provider is used to obtain the intial |
| 1026 // scroll offset. |
| 1027 TEST_F(ElementAnimationsTest, ScrollOffsetTransitionNoImplProvider) { |
| 1028 CreateTestLayer(false, false); |
| 1029 CreateTestImplLayer(LayerTreeType::PENDING); |
| 1030 AttachTimelinePlayerLayer(); |
| 1031 CreateImplTimelineAndPlayer(); |
| 1032 |
| 1033 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1034 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 1035 |
| 1036 EXPECT_TRUE(animations_impl->needs_pending_value_observations()); |
| 1037 EXPECT_FALSE(animations_impl->needs_active_value_observations()); |
| 1038 |
| 1039 auto events = host_impl_->CreateEvents(); |
| 1040 |
| 1041 gfx::ScrollOffset initial_value(500.f, 100.f); |
| 1042 gfx::ScrollOffset target_value(300.f, 200.f); |
| 1043 std::unique_ptr<ScrollOffsetAnimationCurve> curve( |
| 1044 ScrollOffsetAnimationCurve::Create(target_value, |
| 1045 EaseInOutTimingFunction::Create())); |
| 1046 |
| 1047 std::unique_ptr<Animation> animation( |
| 1048 Animation::Create(std::move(curve), 1, 0, TargetProperty::SCROLL_OFFSET)); |
| 1049 animation->set_needs_synchronized_start_time(true); |
| 1050 animations->AddAnimation(std::move(animation)); |
| 1051 |
| 1052 client_.SetScrollOffsetForAnimation(initial_value); |
| 1053 animations->PushPropertiesTo(animations_impl.get()); |
| 1054 animations_impl->ActivateAnimations(); |
| 1055 EXPECT_TRUE(animations_impl->GetAnimation(TargetProperty::SCROLL_OFFSET)); |
| 1056 TimeDelta duration = |
| 1057 animations_impl->GetAnimation(TargetProperty::SCROLL_OFFSET) |
| 1058 ->curve() |
| 1059 ->Duration(); |
| 1060 EXPECT_EQ(duration, animations->GetAnimation(TargetProperty::SCROLL_OFFSET) |
| 1061 ->curve() |
| 1062 ->Duration()); |
| 1063 |
| 1064 animations->Animate(kInitialTickTime); |
| 1065 animations->UpdateState(true, nullptr); |
| 1066 |
| 1067 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1068 EXPECT_EQ(initial_value, |
| 1069 client_.GetScrollOffset(layer_id_, LayerTreeType::ACTIVE)); |
| 1070 EXPECT_EQ(gfx::ScrollOffset(), |
| 1071 client_impl_.GetScrollOffset(layer_id_, LayerTreeType::PENDING)); |
| 1072 |
| 1073 animations_impl->Animate(kInitialTickTime); |
| 1074 |
| 1075 EXPECT_TRUE(animations_impl->HasActiveAnimation()); |
| 1076 EXPECT_EQ(initial_value, |
| 1077 client_impl_.GetScrollOffset(layer_id_, LayerTreeType::PENDING)); |
| 1078 |
| 1079 CreateTestImplLayer(LayerTreeType::ACTIVE); |
| 1080 |
| 1081 animations_impl->UpdateState(true, events.get()); |
| 1082 DCHECK_EQ(1UL, events->events_.size()); |
| 1083 |
| 1084 // Scroll offset animations should not generate property updates. |
| 1085 const AnimationEvent* event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 1086 EXPECT_FALSE(event); |
| 1087 |
| 1088 animations->NotifyAnimationStarted(events->events_[0]); |
| 1089 animations->Animate(kInitialTickTime + duration / 2); |
| 1090 animations->UpdateState(true, nullptr); |
| 1091 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1092 EXPECT_VECTOR2DF_EQ( |
| 1093 gfx::Vector2dF(400.f, 150.f), |
| 1094 client_.GetScrollOffset(layer_id_, LayerTreeType::ACTIVE)); |
| 1095 |
| 1096 animations_impl->Animate(kInitialTickTime + duration / 2); |
| 1097 animations_impl->UpdateState(true, events.get()); |
| 1098 EXPECT_VECTOR2DF_EQ( |
| 1099 gfx::Vector2dF(400.f, 150.f), |
| 1100 client_impl_.GetScrollOffset(layer_id_, LayerTreeType::PENDING)); |
| 1101 event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 1102 EXPECT_FALSE(event); |
| 1103 |
| 1104 animations_impl->Animate(kInitialTickTime + duration); |
| 1105 animations_impl->UpdateState(true, events.get()); |
| 1106 EXPECT_VECTOR2DF_EQ(target_value, client_impl_.GetScrollOffset( |
| 1107 layer_id_, LayerTreeType::PENDING)); |
| 1108 EXPECT_FALSE(animations_impl->HasActiveAnimation()); |
| 1109 event = GetMostRecentPropertyUpdateEvent(events.get()); |
| 1110 EXPECT_FALSE(event); |
| 1111 |
| 1112 animations->Animate(kInitialTickTime + duration); |
| 1113 animations->UpdateState(true, nullptr); |
| 1114 EXPECT_VECTOR2DF_EQ( |
| 1115 target_value, client_.GetScrollOffset(layer_id_, LayerTreeType::ACTIVE)); |
| 1116 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 1117 } |
| 1118 |
| 1119 TEST_F(ElementAnimationsTest, ScrollOffsetRemovalClearsScrollDelta) { |
| 1120 CreateTestLayer(true, false); |
| 1121 AttachTimelinePlayerLayer(); |
| 1122 CreateImplTimelineAndPlayer(); |
| 1123 |
| 1124 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1125 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 1126 |
| 1127 auto events = host_impl_->CreateEvents(); |
| 1128 |
| 1129 // First test the 1-argument version of RemoveAnimation. |
| 1130 gfx::ScrollOffset target_value(300.f, 200.f); |
| 1131 std::unique_ptr<ScrollOffsetAnimationCurve> curve( |
| 1132 ScrollOffsetAnimationCurve::Create(target_value, |
| 1133 EaseInOutTimingFunction::Create())); |
| 1134 |
| 1135 int animation_id = 1; |
| 1136 std::unique_ptr<Animation> animation(Animation::Create( |
| 1137 std::move(curve), animation_id, 0, TargetProperty::SCROLL_OFFSET)); |
| 1138 animation->set_needs_synchronized_start_time(true); |
| 1139 animations->AddAnimation(std::move(animation)); |
| 1140 animations->PushPropertiesTo(animations_impl.get()); |
| 1141 animations_impl->ActivateAnimations(); |
| 1142 EXPECT_FALSE(animations->scroll_offset_animation_was_interrupted()); |
| 1143 EXPECT_FALSE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1144 |
| 1145 animations->RemoveAnimation(animation_id); |
| 1146 EXPECT_TRUE(animations->scroll_offset_animation_was_interrupted()); |
| 1147 |
| 1148 animations->PushPropertiesTo(animations_impl.get()); |
| 1149 EXPECT_TRUE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1150 EXPECT_FALSE(animations->scroll_offset_animation_was_interrupted()); |
| 1151 |
| 1152 animations_impl->ActivateAnimations(); |
| 1153 EXPECT_FALSE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1154 |
| 1155 // Now, test the 2-argument version of RemoveAnimation. |
| 1156 curve = ScrollOffsetAnimationCurve::Create(target_value, |
| 1157 EaseInOutTimingFunction::Create()); |
| 1158 animation = Animation::Create(std::move(curve), animation_id, 0, |
| 1159 TargetProperty::SCROLL_OFFSET); |
| 1160 animation->set_needs_synchronized_start_time(true); |
| 1161 animations->AddAnimation(std::move(animation)); |
| 1162 animations->PushPropertiesTo(animations_impl.get()); |
| 1163 animations_impl->ActivateAnimations(); |
| 1164 EXPECT_FALSE(animations->scroll_offset_animation_was_interrupted()); |
| 1165 EXPECT_FALSE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1166 |
| 1167 animations->RemoveAnimation(animation_id); |
| 1168 EXPECT_TRUE(animations->scroll_offset_animation_was_interrupted()); |
| 1169 |
| 1170 animations->PushPropertiesTo(animations_impl.get()); |
| 1171 EXPECT_TRUE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1172 EXPECT_FALSE(animations->scroll_offset_animation_was_interrupted()); |
| 1173 |
| 1174 animations_impl->ActivateAnimations(); |
| 1175 EXPECT_FALSE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1176 |
| 1177 // Check that removing non-scroll-offset animations does not cause |
| 1178 // scroll_offset_animation_was_interrupted() to get set. |
| 1179 animation_id = |
| 1180 AddAnimatedTransformToElementAnimations(animations.get(), 1.0, 1, 2); |
| 1181 animations->PushPropertiesTo(animations_impl.get()); |
| 1182 animations_impl->ActivateAnimations(); |
| 1183 EXPECT_FALSE(animations->scroll_offset_animation_was_interrupted()); |
| 1184 EXPECT_FALSE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1185 |
| 1186 animations->RemoveAnimation(animation_id); |
| 1187 EXPECT_FALSE(animations->scroll_offset_animation_was_interrupted()); |
| 1188 |
| 1189 animations->PushPropertiesTo(animations_impl.get()); |
| 1190 EXPECT_FALSE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1191 EXPECT_FALSE(animations->scroll_offset_animation_was_interrupted()); |
| 1192 |
| 1193 animations_impl->ActivateAnimations(); |
| 1194 EXPECT_FALSE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1195 |
| 1196 animation_id = |
| 1197 AddAnimatedFilterToElementAnimations(animations.get(), 1.0, 0.1f, 0.2f); |
| 1198 animations->PushPropertiesTo(animations_impl.get()); |
| 1199 animations_impl->ActivateAnimations(); |
| 1200 EXPECT_FALSE(animations->scroll_offset_animation_was_interrupted()); |
| 1201 EXPECT_FALSE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1202 |
| 1203 animations->RemoveAnimation(animation_id); |
| 1204 EXPECT_FALSE(animations->scroll_offset_animation_was_interrupted()); |
| 1205 |
| 1206 animations->PushPropertiesTo(animations_impl.get()); |
| 1207 EXPECT_FALSE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1208 EXPECT_FALSE(animations->scroll_offset_animation_was_interrupted()); |
| 1209 |
| 1210 animations_impl->ActivateAnimations(); |
| 1211 EXPECT_FALSE(animations_impl->scroll_offset_animation_was_interrupted()); |
| 1212 } |
| 1213 |
| 1214 // Tests that impl-only animations lead to start and finished notifications |
| 1215 // on the impl thread animations's animation delegate. |
| 1216 TEST_F(ElementAnimationsTest, |
| 1217 NotificationsForImplOnlyAnimationsAreSentToImplThreadDelegate) { |
| 1218 CreateTestLayer(true, false); |
| 1219 AttachTimelinePlayerLayer(); |
| 1220 CreateImplTimelineAndPlayer(); |
| 1221 |
| 1222 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1223 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 1224 |
| 1225 auto events = host_impl_->CreateEvents(); |
| 1226 |
| 1227 TestAnimationDelegate delegate; |
| 1228 player_impl_->set_layer_animation_delegate(&delegate); |
| 1229 |
| 1230 std::unique_ptr<Animation> to_add(CreateAnimation( |
| 1231 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1232 1, TargetProperty::OPACITY)); |
| 1233 to_add->set_is_impl_only(true); |
| 1234 animations_impl->AddAnimation(std::move(to_add)); |
| 1235 |
| 1236 EXPECT_FALSE(delegate.started()); |
| 1237 EXPECT_FALSE(delegate.finished()); |
| 1238 |
| 1239 animations_impl->Animate(kInitialTickTime); |
| 1240 animations_impl->UpdateState(true, events.get()); |
| 1241 |
| 1242 EXPECT_TRUE(delegate.started()); |
| 1243 EXPECT_FALSE(delegate.finished()); |
| 1244 |
| 1245 events = host_impl_->CreateEvents(); |
| 1246 animations_impl->Animate(kInitialTickTime + |
| 1247 TimeDelta::FromMilliseconds(1000)); |
| 1248 animations_impl->UpdateState(true, events.get()); |
| 1249 |
| 1250 EXPECT_TRUE(delegate.started()); |
| 1251 EXPECT_TRUE(delegate.finished()); |
| 1252 } |
| 1253 |
| 1254 // Tests that specified start times are sent to the main thread delegate |
| 1255 TEST_F(ElementAnimationsTest, SpecifiedStartTimesAreSentToMainThreadDelegate) { |
| 1256 CreateTestLayer(true, false); |
| 1257 AttachTimelinePlayerLayer(); |
| 1258 CreateImplTimelineAndPlayer(); |
| 1259 |
| 1260 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1261 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 1262 |
| 1263 TestAnimationDelegate delegate; |
| 1264 player_->set_layer_animation_delegate(&delegate); |
| 1265 |
| 1266 int animation_id = |
| 1267 AddOpacityTransitionToElementAnimations(animations.get(), 1, 0, 1, false); |
| 1268 |
| 1269 const TimeTicks start_time = TicksFromSecondsF(123); |
| 1270 animations->GetAnimation(TargetProperty::OPACITY)->set_start_time(start_time); |
| 1271 |
| 1272 animations->PushPropertiesTo(animations_impl.get()); |
| 1273 animations_impl->ActivateAnimations(); |
| 1274 |
| 1275 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id)); |
| 1276 EXPECT_EQ(Animation::WAITING_FOR_TARGET_AVAILABILITY, |
| 1277 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 1278 |
| 1279 auto events = host_impl_->CreateEvents(); |
| 1280 animations_impl->Animate(kInitialTickTime); |
| 1281 animations_impl->UpdateState(true, events.get()); |
| 1282 |
| 1283 // Synchronize the start times. |
| 1284 EXPECT_EQ(1u, events->events_.size()); |
| 1285 animations->NotifyAnimationStarted(events->events_[0]); |
| 1286 |
| 1287 // Validate start time on the main thread delegate. |
| 1288 EXPECT_EQ(start_time, delegate.start_time()); |
| 1289 } |
| 1290 |
| 1291 // Tests animations that are waiting for a synchronized start time do not |
| 1292 // finish. |
| 1293 TEST_F(ElementAnimationsTest, |
| 1294 AnimationsWaitingForStartTimeDoNotFinishIfTheyOutwaitTheirFinish) { |
| 1295 CreateTestLayer(false, false); |
| 1296 AttachTimelinePlayerLayer(); |
| 1297 |
| 1298 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1299 |
| 1300 auto events = host_impl_->CreateEvents(); |
| 1301 |
| 1302 std::unique_ptr<Animation> to_add(CreateAnimation( |
| 1303 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1304 1, TargetProperty::OPACITY)); |
| 1305 to_add->set_needs_synchronized_start_time(true); |
| 1306 |
| 1307 // We should pause at the first keyframe indefinitely waiting for that |
| 1308 // animation to start. |
| 1309 animations->AddAnimation(std::move(to_add)); |
| 1310 animations->Animate(kInitialTickTime); |
| 1311 animations->UpdateState(true, events.get()); |
| 1312 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1313 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1314 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 1315 animations->UpdateState(true, events.get()); |
| 1316 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1317 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1318 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(2000)); |
| 1319 animations->UpdateState(true, events.get()); |
| 1320 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1321 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1322 |
| 1323 // Send the synchronized start time. |
| 1324 animations->NotifyAnimationStarted( |
| 1325 AnimationEvent(AnimationEvent::STARTED, 0, 1, TargetProperty::OPACITY, |
| 1326 kInitialTickTime + TimeDelta::FromMilliseconds(2000))); |
| 1327 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(5000)); |
| 1328 animations->UpdateState(true, events.get()); |
| 1329 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1330 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 1331 } |
| 1332 |
| 1333 // Tests that two queued animations affecting the same property run in sequence. |
| 1334 TEST_F(ElementAnimationsTest, TrivialQueuing) { |
| 1335 CreateTestLayer(false, false); |
| 1336 AttachTimelinePlayerLayer(); |
| 1337 |
| 1338 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1339 |
| 1340 auto events = host_impl_->CreateEvents(); |
| 1341 |
| 1342 EXPECT_FALSE(animations->needs_to_start_animations_for_testing()); |
| 1343 |
| 1344 animations->AddAnimation(CreateAnimation( |
| 1345 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1346 1, TargetProperty::OPACITY)); |
| 1347 animations->AddAnimation(CreateAnimation( |
| 1348 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 1.f, 0.5f)), |
| 1349 2, TargetProperty::OPACITY)); |
| 1350 |
| 1351 EXPECT_TRUE(animations->needs_to_start_animations_for_testing()); |
| 1352 |
| 1353 animations->Animate(kInitialTickTime); |
| 1354 |
| 1355 // The second animation still needs to be started. |
| 1356 EXPECT_TRUE(animations->needs_to_start_animations_for_testing()); |
| 1357 |
| 1358 animations->UpdateState(true, events.get()); |
| 1359 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1360 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1361 |
| 1362 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 1363 EXPECT_TRUE(animations->needs_to_start_animations_for_testing()); |
| 1364 animations->UpdateState(true, events.get()); |
| 1365 EXPECT_FALSE(animations->needs_to_start_animations_for_testing()); |
| 1366 |
| 1367 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1368 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1369 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(2000)); |
| 1370 animations->UpdateState(true, events.get()); |
| 1371 EXPECT_EQ(0.5f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1372 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 1373 } |
| 1374 |
| 1375 // Tests interrupting a transition with another transition. |
| 1376 TEST_F(ElementAnimationsTest, Interrupt) { |
| 1377 CreateTestLayer(false, false); |
| 1378 AttachTimelinePlayerLayer(); |
| 1379 |
| 1380 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1381 |
| 1382 auto events = host_impl_->CreateEvents(); |
| 1383 |
| 1384 animations->AddAnimation(CreateAnimation( |
| 1385 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1386 1, TargetProperty::OPACITY)); |
| 1387 animations->Animate(kInitialTickTime); |
| 1388 animations->UpdateState(true, events.get()); |
| 1389 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1390 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1391 |
| 1392 std::unique_ptr<Animation> to_add(CreateAnimation( |
| 1393 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 1.f, 0.5f)), |
| 1394 2, TargetProperty::OPACITY)); |
| 1395 animations->AbortAnimations(TargetProperty::OPACITY); |
| 1396 animations->AddAnimation(std::move(to_add)); |
| 1397 |
| 1398 // Since the previous animation was aborted, the new animation should start |
| 1399 // right in this call to animate. |
| 1400 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 1401 animations->UpdateState(true, events.get()); |
| 1402 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1403 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1404 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1500)); |
| 1405 animations->UpdateState(true, events.get()); |
| 1406 EXPECT_EQ(0.5f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1407 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 1408 } |
| 1409 |
| 1410 // Tests scheduling two animations to run together when only one property is |
| 1411 // free. |
| 1412 TEST_F(ElementAnimationsTest, ScheduleTogetherWhenAPropertyIsBlocked) { |
| 1413 CreateTestLayer(false, false); |
| 1414 AttachTimelinePlayerLayer(); |
| 1415 |
| 1416 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1417 |
| 1418 auto events = host_impl_->CreateEvents(); |
| 1419 |
| 1420 animations->AddAnimation(CreateAnimation( |
| 1421 std::unique_ptr<AnimationCurve>(new FakeTransformTransition(1)), 1, |
| 1422 TargetProperty::TRANSFORM)); |
| 1423 animations->AddAnimation(CreateAnimation( |
| 1424 std::unique_ptr<AnimationCurve>(new FakeTransformTransition(1)), 2, |
| 1425 TargetProperty::TRANSFORM)); |
| 1426 animations->AddAnimation(CreateAnimation( |
| 1427 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1428 2, TargetProperty::OPACITY)); |
| 1429 |
| 1430 animations->Animate(kInitialTickTime); |
| 1431 animations->UpdateState(true, events.get()); |
| 1432 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1433 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1434 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 1435 animations->UpdateState(true, events.get()); |
| 1436 // Should not have started the float transition yet. |
| 1437 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1438 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1439 // The float animation should have started at time 1 and should be done. |
| 1440 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(2000)); |
| 1441 animations->UpdateState(true, events.get()); |
| 1442 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1443 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 1444 } |
| 1445 |
| 1446 // Tests scheduling two animations to run together with different lengths and |
| 1447 // another animation queued to start when the shorter animation finishes (should |
| 1448 // wait for both to finish). |
| 1449 TEST_F(ElementAnimationsTest, ScheduleTogetherWithAnAnimWaiting) { |
| 1450 CreateTestLayer(false, false); |
| 1451 AttachTimelinePlayerLayer(); |
| 1452 |
| 1453 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1454 |
| 1455 auto events = host_impl_->CreateEvents(); |
| 1456 |
| 1457 animations->AddAnimation(CreateAnimation( |
| 1458 std::unique_ptr<AnimationCurve>(new FakeTransformTransition(2)), 1, |
| 1459 TargetProperty::TRANSFORM)); |
| 1460 animations->AddAnimation(CreateAnimation( |
| 1461 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1462 1, TargetProperty::OPACITY)); |
| 1463 animations->AddAnimation(CreateAnimation( |
| 1464 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 1.f, 0.5f)), |
| 1465 2, TargetProperty::OPACITY)); |
| 1466 |
| 1467 // Animations with id 1 should both start now. |
| 1468 animations->Animate(kInitialTickTime); |
| 1469 animations->UpdateState(true, events.get()); |
| 1470 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1471 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1472 // The opacity animation should have finished at time 1, but the group |
| 1473 // of animations with id 1 don't finish until time 2 because of the length |
| 1474 // of the transform animation. |
| 1475 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(2000)); |
| 1476 animations->UpdateState(true, events.get()); |
| 1477 // Should not have started the float transition yet. |
| 1478 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1479 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1480 |
| 1481 // The second opacity animation should start at time 2 and should be done by |
| 1482 // time 3. |
| 1483 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(3000)); |
| 1484 animations->UpdateState(true, events.get()); |
| 1485 EXPECT_EQ(0.5f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1486 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 1487 } |
| 1488 |
| 1489 // Test that a looping animation loops and for the correct number of iterations. |
| 1490 TEST_F(ElementAnimationsTest, TrivialLooping) { |
| 1491 CreateTestLayer(false, false); |
| 1492 AttachTimelinePlayerLayer(); |
| 1493 |
| 1494 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1495 |
| 1496 auto events = host_impl_->CreateEvents(); |
| 1497 |
| 1498 std::unique_ptr<Animation> to_add(CreateAnimation( |
| 1499 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1500 1, TargetProperty::OPACITY)); |
| 1501 to_add->set_iterations(3); |
| 1502 animations->AddAnimation(std::move(to_add)); |
| 1503 |
| 1504 animations->Animate(kInitialTickTime); |
| 1505 animations->UpdateState(true, events.get()); |
| 1506 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1507 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1508 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1250)); |
| 1509 animations->UpdateState(true, events.get()); |
| 1510 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1511 EXPECT_EQ(0.25f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1512 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1750)); |
| 1513 animations->UpdateState(true, events.get()); |
| 1514 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1515 EXPECT_EQ(0.75f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1516 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(2250)); |
| 1517 animations->UpdateState(true, events.get()); |
| 1518 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1519 EXPECT_EQ(0.25f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1520 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(2750)); |
| 1521 animations->UpdateState(true, events.get()); |
| 1522 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1523 EXPECT_EQ(0.75f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1524 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(3000)); |
| 1525 animations->UpdateState(true, events.get()); |
| 1526 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 1527 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1528 |
| 1529 // Just be extra sure. |
| 1530 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(4000)); |
| 1531 animations->UpdateState(true, events.get()); |
| 1532 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1533 } |
| 1534 |
| 1535 // Test that an infinitely looping animation does indeed go until aborted. |
| 1536 TEST_F(ElementAnimationsTest, InfiniteLooping) { |
| 1537 CreateTestLayer(false, false); |
| 1538 AttachTimelinePlayerLayer(); |
| 1539 |
| 1540 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1541 |
| 1542 auto events = host_impl_->CreateEvents(); |
| 1543 |
| 1544 std::unique_ptr<Animation> to_add(CreateAnimation( |
| 1545 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1546 1, TargetProperty::OPACITY)); |
| 1547 to_add->set_iterations(-1); |
| 1548 animations->AddAnimation(std::move(to_add)); |
| 1549 |
| 1550 animations->Animate(kInitialTickTime); |
| 1551 animations->UpdateState(true, events.get()); |
| 1552 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1553 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1554 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1250)); |
| 1555 animations->UpdateState(true, events.get()); |
| 1556 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1557 EXPECT_EQ(0.25f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1558 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1750)); |
| 1559 animations->UpdateState(true, events.get()); |
| 1560 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1561 EXPECT_EQ(0.75f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1562 |
| 1563 animations->Animate(kInitialTickTime + |
| 1564 TimeDelta::FromMilliseconds(1073741824250)); |
| 1565 animations->UpdateState(true, events.get()); |
| 1566 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1567 EXPECT_EQ(0.25f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1568 animations->Animate(kInitialTickTime + |
| 1569 TimeDelta::FromMilliseconds(1073741824750)); |
| 1570 animations->UpdateState(true, events.get()); |
| 1571 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1572 EXPECT_EQ(0.75f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1573 |
| 1574 EXPECT_TRUE(animations->GetAnimation(TargetProperty::OPACITY)); |
| 1575 animations->GetAnimation(TargetProperty::OPACITY) |
| 1576 ->SetRunState(Animation::ABORTED, |
| 1577 kInitialTickTime + TimeDelta::FromMilliseconds(750)); |
| 1578 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 1579 EXPECT_EQ(0.75f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1580 } |
| 1581 |
| 1582 // Test that pausing and resuming work as expected. |
| 1583 TEST_F(ElementAnimationsTest, PauseResume) { |
| 1584 CreateTestLayer(false, false); |
| 1585 AttachTimelinePlayerLayer(); |
| 1586 |
| 1587 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1588 |
| 1589 auto events = host_impl_->CreateEvents(); |
| 1590 |
| 1591 animations->AddAnimation(CreateAnimation( |
| 1592 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1593 1, TargetProperty::OPACITY)); |
| 1594 |
| 1595 animations->Animate(kInitialTickTime); |
| 1596 animations->UpdateState(true, events.get()); |
| 1597 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1598 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1599 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 1600 animations->UpdateState(true, events.get()); |
| 1601 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1602 EXPECT_EQ(0.5f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1603 |
| 1604 EXPECT_TRUE(animations->GetAnimation(TargetProperty::OPACITY)); |
| 1605 animations->GetAnimation(TargetProperty::OPACITY) |
| 1606 ->SetRunState(Animation::PAUSED, |
| 1607 kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 1608 |
| 1609 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1024000)); |
| 1610 animations->UpdateState(true, events.get()); |
| 1611 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1612 EXPECT_EQ(0.5f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1613 |
| 1614 EXPECT_TRUE(animations->GetAnimation(TargetProperty::OPACITY)); |
| 1615 animations->GetAnimation(TargetProperty::OPACITY) |
| 1616 ->SetRunState(Animation::RUNNING, |
| 1617 kInitialTickTime + TimeDelta::FromMilliseconds(1024000)); |
| 1618 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1024250)); |
| 1619 animations->UpdateState(true, events.get()); |
| 1620 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1621 EXPECT_EQ(0.75f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1622 |
| 1623 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1024500)); |
| 1624 animations->UpdateState(true, events.get()); |
| 1625 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 1626 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1627 } |
| 1628 |
| 1629 TEST_F(ElementAnimationsTest, AbortAGroupedAnimation) { |
| 1630 CreateTestLayer(false, false); |
| 1631 AttachTimelinePlayerLayer(); |
| 1632 |
| 1633 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1634 |
| 1635 auto events = host_impl_->CreateEvents(); |
| 1636 |
| 1637 const int animation_id = 2; |
| 1638 animations->AddAnimation(Animation::Create( |
| 1639 std::unique_ptr<AnimationCurve>(new FakeTransformTransition(1)), 1, 1, |
| 1640 TargetProperty::TRANSFORM)); |
| 1641 animations->AddAnimation(Animation::Create( |
| 1642 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(2.0, 0.f, 1.f)), |
| 1643 animation_id, 1, TargetProperty::OPACITY)); |
| 1644 animations->AddAnimation(Animation::Create( |
| 1645 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 1.f, 0.75f)), |
| 1646 3, 2, TargetProperty::OPACITY)); |
| 1647 |
| 1648 animations->Animate(kInitialTickTime); |
| 1649 animations->UpdateState(true, events.get()); |
| 1650 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1651 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1652 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 1653 animations->UpdateState(true, events.get()); |
| 1654 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1655 EXPECT_EQ(0.5f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1656 |
| 1657 EXPECT_TRUE(animations->GetAnimationById(animation_id)); |
| 1658 animations->GetAnimationById(animation_id) |
| 1659 ->SetRunState(Animation::ABORTED, |
| 1660 kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 1661 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 1662 animations->UpdateState(true, events.get()); |
| 1663 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1664 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1665 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(2000)); |
| 1666 animations->UpdateState(true, events.get()); |
| 1667 EXPECT_TRUE(!animations->HasActiveAnimation()); |
| 1668 EXPECT_EQ(0.75f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1669 } |
| 1670 |
| 1671 TEST_F(ElementAnimationsTest, PushUpdatesWhenSynchronizedStartTimeNeeded) { |
| 1672 CreateTestLayer(true, false); |
| 1673 AttachTimelinePlayerLayer(); |
| 1674 CreateImplTimelineAndPlayer(); |
| 1675 |
| 1676 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1677 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 1678 |
| 1679 auto events = host_impl_->CreateEvents(); |
| 1680 |
| 1681 std::unique_ptr<Animation> to_add(CreateAnimation( |
| 1682 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(2.0, 0.f, 1.f)), |
| 1683 0, TargetProperty::OPACITY)); |
| 1684 to_add->set_needs_synchronized_start_time(true); |
| 1685 animations->AddAnimation(std::move(to_add)); |
| 1686 |
| 1687 animations->Animate(kInitialTickTime); |
| 1688 animations->UpdateState(true, events.get()); |
| 1689 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1690 Animation* active_animation = |
| 1691 animations->GetAnimation(TargetProperty::OPACITY); |
| 1692 EXPECT_TRUE(active_animation); |
| 1693 EXPECT_TRUE(active_animation->needs_synchronized_start_time()); |
| 1694 |
| 1695 animations->PushPropertiesTo(animations_impl.get()); |
| 1696 animations_impl->ActivateAnimations(); |
| 1697 |
| 1698 active_animation = animations_impl->GetAnimation(TargetProperty::OPACITY); |
| 1699 EXPECT_TRUE(active_animation); |
| 1700 EXPECT_EQ(Animation::WAITING_FOR_TARGET_AVAILABILITY, |
| 1701 active_animation->run_state()); |
| 1702 } |
| 1703 |
| 1704 // Tests that skipping a call to UpdateState works as expected. |
| 1705 TEST_F(ElementAnimationsTest, SkipUpdateState) { |
| 1706 CreateTestLayer(true, false); |
| 1707 AttachTimelinePlayerLayer(); |
| 1708 |
| 1709 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1710 |
| 1711 auto events = host_impl_->CreateEvents(); |
| 1712 |
| 1713 std::unique_ptr<Animation> first_animation(CreateAnimation( |
| 1714 std::unique_ptr<AnimationCurve>(new FakeTransformTransition(1)), 1, |
| 1715 TargetProperty::TRANSFORM)); |
| 1716 first_animation->set_is_controlling_instance_for_test(true); |
| 1717 animations->AddAnimation(std::move(first_animation)); |
| 1718 |
| 1719 animations->Animate(kInitialTickTime); |
| 1720 animations->UpdateState(true, events.get()); |
| 1721 |
| 1722 std::unique_ptr<Animation> second_animation(CreateAnimation( |
| 1723 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1724 2, TargetProperty::OPACITY)); |
| 1725 second_animation->set_is_controlling_instance_for_test(true); |
| 1726 animations->AddAnimation(std::move(second_animation)); |
| 1727 |
| 1728 // Animate but don't UpdateState. |
| 1729 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 1730 |
| 1731 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(2000)); |
| 1732 events = host_impl_->CreateEvents(); |
| 1733 animations->UpdateState(true, events.get()); |
| 1734 |
| 1735 // Should have one STARTED event and one FINISHED event. |
| 1736 EXPECT_EQ(2u, events->events_.size()); |
| 1737 EXPECT_NE(events->events_[0].type, events->events_[1].type); |
| 1738 |
| 1739 // The float transition should still be at its starting point. |
| 1740 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 1741 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1742 |
| 1743 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(3000)); |
| 1744 animations->UpdateState(true, events.get()); |
| 1745 |
| 1746 // The float tranisition should now be done. |
| 1747 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1748 EXPECT_FALSE(animations->HasActiveAnimation()); |
| 1749 } |
| 1750 |
| 1751 // Tests that an animation animations with only a pending observer gets ticked |
| 1752 // but doesn't progress animations past the STARTING state. |
| 1753 TEST_F(ElementAnimationsTest, InactiveObserverGetsTicked) { |
| 1754 AttachTimelinePlayerLayer(); |
| 1755 CreateImplTimelineAndPlayer(); |
| 1756 |
| 1757 scoped_refptr<ElementAnimations> animations = element_animations_impl(); |
| 1758 |
| 1759 auto events = host_impl_->CreateEvents(); |
| 1760 |
| 1761 const int id = 1; |
| 1762 animations->AddAnimation(CreateAnimation( |
| 1763 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.5f, 1.f)), |
| 1764 id, TargetProperty::OPACITY)); |
| 1765 |
| 1766 // Without an observer, the animation shouldn't progress to the STARTING |
| 1767 // state. |
| 1768 animations->Animate(kInitialTickTime); |
| 1769 animations->UpdateState(true, events.get()); |
| 1770 EXPECT_EQ(0u, events->events_.size()); |
| 1771 EXPECT_EQ(Animation::WAITING_FOR_TARGET_AVAILABILITY, |
| 1772 animations->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 1773 |
| 1774 // animations->set_needs_pending_value_observations(true); |
| 1775 CreateTestImplLayer(LayerTreeType::PENDING); |
| 1776 |
| 1777 // With only a pending observer, the animation should progress to the |
| 1778 // STARTING state and get ticked at its starting point, but should not |
| 1779 // progress to RUNNING. |
| 1780 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 1781 animations->UpdateState(true, events.get()); |
| 1782 EXPECT_EQ(0u, events->events_.size()); |
| 1783 EXPECT_EQ(Animation::STARTING, |
| 1784 animations->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 1785 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 1786 |
| 1787 // Even when already in the STARTING state, the animation should stay |
| 1788 // there, and shouldn't be ticked past its starting point. |
| 1789 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(2000)); |
| 1790 animations->UpdateState(true, events.get()); |
| 1791 EXPECT_EQ(0u, events->events_.size()); |
| 1792 EXPECT_EQ(Animation::STARTING, |
| 1793 animations->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 1794 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 1795 |
| 1796 // animations->set_needs_active_value_observations(true); |
| 1797 CreateTestImplLayer(LayerTreeType::ACTIVE); |
| 1798 |
| 1799 // Now that an active observer has been added, the animation should still |
| 1800 // initially tick at its starting point, but should now progress to RUNNING. |
| 1801 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(3000)); |
| 1802 animations->UpdateState(true, events.get()); |
| 1803 EXPECT_EQ(1u, events->events_.size()); |
| 1804 EXPECT_EQ(Animation::RUNNING, |
| 1805 animations->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 1806 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 1807 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1808 |
| 1809 // The animation should now tick past its starting point. |
| 1810 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(3500)); |
| 1811 EXPECT_NE(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 1812 EXPECT_NE(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 1813 } |
| 1814 |
| 1815 TEST_F(ElementAnimationsTest, TransformAnimationBounds) { |
| 1816 AttachTimelinePlayerLayer(); |
| 1817 CreateImplTimelineAndPlayer(); |
| 1818 |
| 1819 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 1820 |
| 1821 std::unique_ptr<KeyframedTransformAnimationCurve> curve1( |
| 1822 KeyframedTransformAnimationCurve::Create()); |
| 1823 |
| 1824 TransformOperations operations1; |
| 1825 curve1->AddKeyframe( |
| 1826 TransformKeyframe::Create(base::TimeDelta(), operations1, nullptr)); |
| 1827 operations1.AppendTranslate(10.0, 15.0, 0.0); |
| 1828 curve1->AddKeyframe(TransformKeyframe::Create( |
| 1829 base::TimeDelta::FromSecondsD(1.0), operations1, nullptr)); |
| 1830 |
| 1831 std::unique_ptr<Animation> animation( |
| 1832 Animation::Create(std::move(curve1), 1, 1, TargetProperty::TRANSFORM)); |
| 1833 animations_impl->AddAnimation(std::move(animation)); |
| 1834 |
| 1835 std::unique_ptr<KeyframedTransformAnimationCurve> curve2( |
| 1836 KeyframedTransformAnimationCurve::Create()); |
| 1837 |
| 1838 TransformOperations operations2; |
| 1839 curve2->AddKeyframe( |
| 1840 TransformKeyframe::Create(base::TimeDelta(), operations2, nullptr)); |
| 1841 operations2.AppendScale(2.0, 3.0, 4.0); |
| 1842 curve2->AddKeyframe(TransformKeyframe::Create( |
| 1843 base::TimeDelta::FromSecondsD(1.0), operations2, nullptr)); |
| 1844 |
| 1845 animation = |
| 1846 Animation::Create(std::move(curve2), 2, 2, TargetProperty::TRANSFORM); |
| 1847 animations_impl->AddAnimation(std::move(animation)); |
| 1848 |
| 1849 gfx::BoxF box(1.f, 2.f, -1.f, 3.f, 4.f, 5.f); |
| 1850 gfx::BoxF bounds; |
| 1851 |
| 1852 EXPECT_TRUE(animations_impl->TransformAnimationBoundsForBox(box, &bounds)); |
| 1853 EXPECT_EQ(gfx::BoxF(1.f, 2.f, -4.f, 13.f, 19.f, 20.f).ToString(), |
| 1854 bounds.ToString()); |
| 1855 |
| 1856 animations_impl->GetAnimationById(1)->SetRunState(Animation::FINISHED, |
| 1857 TicksFromSecondsF(0.0)); |
| 1858 |
| 1859 // Only the unfinished animation should affect the animated bounds. |
| 1860 EXPECT_TRUE(animations_impl->TransformAnimationBoundsForBox(box, &bounds)); |
| 1861 EXPECT_EQ(gfx::BoxF(1.f, 2.f, -4.f, 7.f, 16.f, 20.f).ToString(), |
| 1862 bounds.ToString()); |
| 1863 |
| 1864 animations_impl->GetAnimationById(2)->SetRunState(Animation::FINISHED, |
| 1865 TicksFromSecondsF(0.0)); |
| 1866 |
| 1867 // There are no longer any running animations. |
| 1868 EXPECT_FALSE(animations_impl->HasTransformAnimationThatInflatesBounds()); |
| 1869 |
| 1870 // Add an animation whose bounds we don't yet support computing. |
| 1871 std::unique_ptr<KeyframedTransformAnimationCurve> curve3( |
| 1872 KeyframedTransformAnimationCurve::Create()); |
| 1873 TransformOperations operations3; |
| 1874 gfx::Transform transform3; |
| 1875 transform3.Scale3d(1.0, 2.0, 3.0); |
| 1876 curve3->AddKeyframe( |
| 1877 TransformKeyframe::Create(base::TimeDelta(), operations3, nullptr)); |
| 1878 operations3.AppendMatrix(transform3); |
| 1879 curve3->AddKeyframe(TransformKeyframe::Create( |
| 1880 base::TimeDelta::FromSecondsD(1.0), operations3, nullptr)); |
| 1881 animation = |
| 1882 Animation::Create(std::move(curve3), 3, 3, TargetProperty::TRANSFORM); |
| 1883 animations_impl->AddAnimation(std::move(animation)); |
| 1884 EXPECT_FALSE(animations_impl->TransformAnimationBoundsForBox(box, &bounds)); |
| 1885 } |
| 1886 |
| 1887 // Tests that AbortAnimations aborts all animations targeting the specified |
| 1888 // property. |
| 1889 TEST_F(ElementAnimationsTest, AbortAnimations) { |
| 1890 CreateTestLayer(false, false); |
| 1891 AttachTimelinePlayerLayer(); |
| 1892 |
| 1893 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1894 |
| 1895 // Start with several animations, and allow some of them to reach the finished |
| 1896 // state. |
| 1897 animations->AddAnimation(Animation::Create( |
| 1898 std::unique_ptr<AnimationCurve>(new FakeTransformTransition(1.0)), 1, 1, |
| 1899 TargetProperty::TRANSFORM)); |
| 1900 animations->AddAnimation(Animation::Create( |
| 1901 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1902 2, 2, TargetProperty::OPACITY)); |
| 1903 animations->AddAnimation(Animation::Create( |
| 1904 std::unique_ptr<AnimationCurve>(new FakeTransformTransition(1.0)), 3, 3, |
| 1905 TargetProperty::TRANSFORM)); |
| 1906 animations->AddAnimation(Animation::Create( |
| 1907 std::unique_ptr<AnimationCurve>(new FakeTransformTransition(2.0)), 4, 4, |
| 1908 TargetProperty::TRANSFORM)); |
| 1909 animations->AddAnimation(Animation::Create( |
| 1910 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 1911 5, 5, TargetProperty::OPACITY)); |
| 1912 |
| 1913 animations->Animate(kInitialTickTime); |
| 1914 animations->UpdateState(true, nullptr); |
| 1915 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 1916 animations->UpdateState(true, nullptr); |
| 1917 |
| 1918 EXPECT_EQ(Animation::FINISHED, animations->GetAnimationById(1)->run_state()); |
| 1919 EXPECT_EQ(Animation::FINISHED, animations->GetAnimationById(2)->run_state()); |
| 1920 EXPECT_EQ(Animation::RUNNING, animations->GetAnimationById(3)->run_state()); |
| 1921 EXPECT_EQ(Animation::WAITING_FOR_TARGET_AVAILABILITY, |
| 1922 animations->GetAnimationById(4)->run_state()); |
| 1923 EXPECT_EQ(Animation::RUNNING, animations->GetAnimationById(5)->run_state()); |
| 1924 |
| 1925 animations->AbortAnimations(TargetProperty::TRANSFORM); |
| 1926 |
| 1927 // Only un-finished TRANSFORM animations should have been aborted. |
| 1928 EXPECT_EQ(Animation::FINISHED, animations->GetAnimationById(1)->run_state()); |
| 1929 EXPECT_EQ(Animation::FINISHED, animations->GetAnimationById(2)->run_state()); |
| 1930 EXPECT_EQ(Animation::ABORTED, animations->GetAnimationById(3)->run_state()); |
| 1931 EXPECT_EQ(Animation::ABORTED, animations->GetAnimationById(4)->run_state()); |
| 1932 EXPECT_EQ(Animation::RUNNING, animations->GetAnimationById(5)->run_state()); |
| 1933 } |
| 1934 |
| 1935 // An animation aborted on the main thread should get deleted on both threads. |
| 1936 TEST_F(ElementAnimationsTest, MainThreadAbortedAnimationGetsDeleted) { |
| 1937 CreateTestLayer(true, false); |
| 1938 AttachTimelinePlayerLayer(); |
| 1939 CreateImplTimelineAndPlayer(); |
| 1940 |
| 1941 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1942 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 1943 |
| 1944 int animation_id = AddOpacityTransitionToElementAnimations( |
| 1945 animations.get(), 1.0, 0.f, 1.f, false); |
| 1946 |
| 1947 animations->PushPropertiesTo(animations_impl.get()); |
| 1948 animations_impl->ActivateAnimations(); |
| 1949 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id)); |
| 1950 |
| 1951 animations->AbortAnimations(TargetProperty::OPACITY); |
| 1952 EXPECT_EQ(Animation::ABORTED, |
| 1953 animations->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 1954 EXPECT_FALSE(host_->animation_waiting_for_deletion()); |
| 1955 EXPECT_FALSE(host_impl_->animation_waiting_for_deletion()); |
| 1956 |
| 1957 animations->Animate(kInitialTickTime); |
| 1958 animations->UpdateState(true, nullptr); |
| 1959 EXPECT_FALSE(host_->animation_waiting_for_deletion()); |
| 1960 EXPECT_EQ(Animation::ABORTED, |
| 1961 animations->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 1962 |
| 1963 animations->PushPropertiesTo(animations_impl.get()); |
| 1964 EXPECT_FALSE(animations->GetAnimationById(animation_id)); |
| 1965 EXPECT_FALSE(animations_impl->GetAnimationById(animation_id)); |
| 1966 } |
| 1967 |
| 1968 // An animation aborted on the impl thread should get deleted on both threads. |
| 1969 TEST_F(ElementAnimationsTest, ImplThreadAbortedAnimationGetsDeleted) { |
| 1970 CreateTestLayer(true, false); |
| 1971 AttachTimelinePlayerLayer(); |
| 1972 CreateImplTimelineAndPlayer(); |
| 1973 |
| 1974 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 1975 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 1976 |
| 1977 TestAnimationDelegate delegate; |
| 1978 player_->set_layer_animation_delegate(&delegate); |
| 1979 |
| 1980 int animation_id = AddOpacityTransitionToElementAnimations( |
| 1981 animations.get(), 1.0, 0.f, 1.f, false); |
| 1982 |
| 1983 animations->PushPropertiesTo(animations_impl.get()); |
| 1984 animations_impl->ActivateAnimations(); |
| 1985 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id)); |
| 1986 |
| 1987 animations_impl->AbortAnimations(TargetProperty::OPACITY); |
| 1988 EXPECT_EQ( |
| 1989 Animation::ABORTED, |
| 1990 animations_impl->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 1991 EXPECT_FALSE(host_->animation_waiting_for_deletion()); |
| 1992 EXPECT_FALSE(host_impl_->animation_waiting_for_deletion()); |
| 1993 |
| 1994 auto events = host_impl_->CreateEvents(); |
| 1995 animations_impl->Animate(kInitialTickTime); |
| 1996 animations_impl->UpdateState(true, events.get()); |
| 1997 EXPECT_TRUE(host_impl_->animation_waiting_for_deletion()); |
| 1998 EXPECT_EQ(1u, events->events_.size()); |
| 1999 EXPECT_EQ(AnimationEvent::ABORTED, events->events_[0].type); |
| 2000 EXPECT_EQ( |
| 2001 Animation::WAITING_FOR_DELETION, |
| 2002 animations_impl->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 2003 |
| 2004 animations->NotifyAnimationAborted(events->events_[0]); |
| 2005 EXPECT_EQ(Animation::ABORTED, |
| 2006 animations->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 2007 EXPECT_TRUE(delegate.aborted()); |
| 2008 |
| 2009 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 2010 animations->UpdateState(true, nullptr); |
| 2011 EXPECT_TRUE(host_->animation_waiting_for_deletion()); |
| 2012 EXPECT_EQ(Animation::WAITING_FOR_DELETION, |
| 2013 animations->GetAnimation(TargetProperty::OPACITY)->run_state()); |
| 2014 |
| 2015 animations->PushPropertiesTo(animations_impl.get()); |
| 2016 animations_impl->ActivateAnimations(); |
| 2017 EXPECT_FALSE(animations->GetAnimationById(animation_id)); |
| 2018 EXPECT_FALSE(animations_impl->GetAnimationById(animation_id)); |
| 2019 } |
| 2020 |
| 2021 // Test that an impl-only scroll offset animation that needs to be completed on |
| 2022 // the main thread gets deleted. |
| 2023 TEST_F(ElementAnimationsTest, ImplThreadTakeoverAnimationGetsDeleted) { |
| 2024 CreateTestLayer(true, false); |
| 2025 AttachTimelinePlayerLayer(); |
| 2026 CreateImplTimelineAndPlayer(); |
| 2027 |
| 2028 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 2029 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2030 |
| 2031 TestAnimationDelegate delegate_impl; |
| 2032 player_impl_->set_layer_animation_delegate(&delegate_impl); |
| 2033 TestAnimationDelegate delegate; |
| 2034 player_->set_layer_animation_delegate(&delegate); |
| 2035 |
| 2036 // Add impl-only scroll offset animation. |
| 2037 const int animation_id = 1; |
| 2038 gfx::ScrollOffset initial_value(100.f, 300.f); |
| 2039 gfx::ScrollOffset target_value(300.f, 200.f); |
| 2040 std::unique_ptr<ScrollOffsetAnimationCurve> curve( |
| 2041 ScrollOffsetAnimationCurve::Create(target_value, |
| 2042 EaseInOutTimingFunction::Create())); |
| 2043 curve->SetInitialValue(initial_value); |
| 2044 std::unique_ptr<Animation> animation(Animation::Create( |
| 2045 std::move(curve), animation_id, 0, TargetProperty::SCROLL_OFFSET)); |
| 2046 animation->set_start_time(TicksFromSecondsF(123)); |
| 2047 animation->set_is_impl_only(true); |
| 2048 animations_impl->AddAnimation(std::move(animation)); |
| 2049 |
| 2050 animations->PushPropertiesTo(animations_impl.get()); |
| 2051 animations_impl->ActivateAnimations(); |
| 2052 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id)); |
| 2053 |
| 2054 const bool needs_completion = true; |
| 2055 animations_impl->AbortAnimations(TargetProperty::SCROLL_OFFSET, |
| 2056 needs_completion); |
| 2057 EXPECT_EQ(Animation::ABORTED_BUT_NEEDS_COMPLETION, |
| 2058 animations_impl->GetAnimation(TargetProperty::SCROLL_OFFSET) |
| 2059 ->run_state()); |
| 2060 EXPECT_FALSE(host_->animation_waiting_for_deletion()); |
| 2061 EXPECT_FALSE(host_impl_->animation_waiting_for_deletion()); |
| 2062 |
| 2063 auto events = host_impl_->CreateEvents(); |
| 2064 animations_impl->Animate(kInitialTickTime); |
| 2065 animations_impl->UpdateState(true, events.get()); |
| 2066 EXPECT_TRUE(delegate_impl.finished()); |
| 2067 EXPECT_TRUE(host_impl_->animation_waiting_for_deletion()); |
| 2068 EXPECT_EQ(1u, events->events_.size()); |
| 2069 EXPECT_EQ(AnimationEvent::TAKEOVER, events->events_[0].type); |
| 2070 EXPECT_EQ(123, events->events_[0].animation_start_time); |
| 2071 EXPECT_EQ( |
| 2072 target_value, |
| 2073 events->events_[0].curve->ToScrollOffsetAnimationCurve()->target_value()); |
| 2074 EXPECT_EQ(Animation::WAITING_FOR_DELETION, |
| 2075 animations_impl->GetAnimation(TargetProperty::SCROLL_OFFSET) |
| 2076 ->run_state()); |
| 2077 |
| 2078 animations->NotifyAnimationTakeover(events->events_[0]); |
| 2079 EXPECT_TRUE(delegate.takeover()); |
| 2080 |
| 2081 animations->PushPropertiesTo(animations_impl.get()); |
| 2082 animations_impl->ActivateAnimations(); |
| 2083 EXPECT_FALSE(animations->GetAnimationById(animation_id)); |
| 2084 EXPECT_FALSE(animations_impl->GetAnimationById(animation_id)); |
| 2085 } |
| 2086 |
| 2087 // Ensure that we only generate FINISHED events for animations in a group |
| 2088 // once all animations in that group are finished. |
| 2089 TEST_F(ElementAnimationsTest, FinishedEventsForGroup) { |
| 2090 CreateTestLayer(true, false); |
| 2091 AttachTimelinePlayerLayer(); |
| 2092 CreateImplTimelineAndPlayer(); |
| 2093 |
| 2094 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2095 |
| 2096 auto events = host_impl_->CreateEvents(); |
| 2097 |
| 2098 const int group_id = 1; |
| 2099 |
| 2100 // Add two animations with the same group id but different durations. |
| 2101 std::unique_ptr<Animation> first_animation(Animation::Create( |
| 2102 std::unique_ptr<AnimationCurve>(new FakeTransformTransition(2.0)), 1, |
| 2103 group_id, TargetProperty::TRANSFORM)); |
| 2104 first_animation->set_is_controlling_instance_for_test(true); |
| 2105 animations_impl->AddAnimation(std::move(first_animation)); |
| 2106 |
| 2107 std::unique_ptr<Animation> second_animation(Animation::Create( |
| 2108 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 2109 2, group_id, TargetProperty::OPACITY)); |
| 2110 second_animation->set_is_controlling_instance_for_test(true); |
| 2111 animations_impl->AddAnimation(std::move(second_animation)); |
| 2112 |
| 2113 animations_impl->Animate(kInitialTickTime); |
| 2114 animations_impl->UpdateState(true, events.get()); |
| 2115 |
| 2116 // Both animations should have started. |
| 2117 EXPECT_EQ(2u, events->events_.size()); |
| 2118 EXPECT_EQ(AnimationEvent::STARTED, events->events_[0].type); |
| 2119 EXPECT_EQ(AnimationEvent::STARTED, events->events_[1].type); |
| 2120 |
| 2121 events = host_impl_->CreateEvents(); |
| 2122 animations_impl->Animate(kInitialTickTime + |
| 2123 TimeDelta::FromMilliseconds(1000)); |
| 2124 animations_impl->UpdateState(true, events.get()); |
| 2125 |
| 2126 // The opacity animation should be finished, but should not have generated |
| 2127 // a FINISHED event yet. |
| 2128 EXPECT_EQ(0u, events->events_.size()); |
| 2129 EXPECT_EQ(Animation::FINISHED, |
| 2130 animations_impl->GetAnimationById(2)->run_state()); |
| 2131 EXPECT_EQ(Animation::RUNNING, |
| 2132 animations_impl->GetAnimationById(1)->run_state()); |
| 2133 |
| 2134 animations_impl->Animate(kInitialTickTime + |
| 2135 TimeDelta::FromMilliseconds(2000)); |
| 2136 animations_impl->UpdateState(true, events.get()); |
| 2137 |
| 2138 // Both animations should have generated FINISHED events. |
| 2139 EXPECT_EQ(2u, events->events_.size()); |
| 2140 EXPECT_EQ(AnimationEvent::FINISHED, events->events_[0].type); |
| 2141 EXPECT_EQ(AnimationEvent::FINISHED, events->events_[1].type); |
| 2142 } |
| 2143 |
| 2144 // Ensure that when a group has a mix of aborted and finished animations, |
| 2145 // we generate a FINISHED event for the finished animation and an ABORTED |
| 2146 // event for the aborted animation. |
| 2147 TEST_F(ElementAnimationsTest, FinishedAndAbortedEventsForGroup) { |
| 2148 CreateTestLayer(true, false); |
| 2149 AttachTimelinePlayerLayer(); |
| 2150 CreateImplTimelineAndPlayer(); |
| 2151 |
| 2152 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2153 |
| 2154 auto events = host_impl_->CreateEvents(); |
| 2155 |
| 2156 // Add two animations with the same group id. |
| 2157 std::unique_ptr<Animation> first_animation(CreateAnimation( |
| 2158 std::unique_ptr<AnimationCurve>(new FakeTransformTransition(1.0)), 1, |
| 2159 TargetProperty::TRANSFORM)); |
| 2160 first_animation->set_is_controlling_instance_for_test(true); |
| 2161 animations_impl->AddAnimation(std::move(first_animation)); |
| 2162 |
| 2163 std::unique_ptr<Animation> second_animation(CreateAnimation( |
| 2164 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 2165 1, TargetProperty::OPACITY)); |
| 2166 second_animation->set_is_controlling_instance_for_test(true); |
| 2167 animations_impl->AddAnimation(std::move(second_animation)); |
| 2168 |
| 2169 animations_impl->Animate(kInitialTickTime); |
| 2170 animations_impl->UpdateState(true, events.get()); |
| 2171 |
| 2172 // Both animations should have started. |
| 2173 EXPECT_EQ(2u, events->events_.size()); |
| 2174 EXPECT_EQ(AnimationEvent::STARTED, events->events_[0].type); |
| 2175 EXPECT_EQ(AnimationEvent::STARTED, events->events_[1].type); |
| 2176 |
| 2177 animations_impl->AbortAnimations(TargetProperty::OPACITY); |
| 2178 |
| 2179 events = host_impl_->CreateEvents(); |
| 2180 animations_impl->Animate(kInitialTickTime + |
| 2181 TimeDelta::FromMilliseconds(1000)); |
| 2182 animations_impl->UpdateState(true, events.get()); |
| 2183 |
| 2184 // We should have exactly 2 events: a FINISHED event for the tranform |
| 2185 // animation, and an ABORTED event for the opacity animation. |
| 2186 EXPECT_EQ(2u, events->events_.size()); |
| 2187 EXPECT_EQ(AnimationEvent::FINISHED, events->events_[0].type); |
| 2188 EXPECT_EQ(TargetProperty::TRANSFORM, events->events_[0].target_property); |
| 2189 EXPECT_EQ(AnimationEvent::ABORTED, events->events_[1].type); |
| 2190 EXPECT_EQ(TargetProperty::OPACITY, events->events_[1].target_property); |
| 2191 } |
| 2192 |
| 2193 TEST_F(ElementAnimationsTest, HasAnimationThatAffectsScale) { |
| 2194 CreateTestLayer(true, false); |
| 2195 AttachTimelinePlayerLayer(); |
| 2196 CreateImplTimelineAndPlayer(); |
| 2197 |
| 2198 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2199 |
| 2200 EXPECT_FALSE(animations_impl->HasAnimationThatAffectsScale()); |
| 2201 |
| 2202 animations_impl->AddAnimation(CreateAnimation( |
| 2203 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 2204 1, TargetProperty::OPACITY)); |
| 2205 |
| 2206 // Opacity animations don't affect scale. |
| 2207 EXPECT_FALSE(animations_impl->HasAnimationThatAffectsScale()); |
| 2208 |
| 2209 std::unique_ptr<KeyframedTransformAnimationCurve> curve1( |
| 2210 KeyframedTransformAnimationCurve::Create()); |
| 2211 |
| 2212 TransformOperations operations1; |
| 2213 curve1->AddKeyframe( |
| 2214 TransformKeyframe::Create(base::TimeDelta(), operations1, nullptr)); |
| 2215 operations1.AppendTranslate(10.0, 15.0, 0.0); |
| 2216 curve1->AddKeyframe(TransformKeyframe::Create( |
| 2217 base::TimeDelta::FromSecondsD(1.0), operations1, nullptr)); |
| 2218 |
| 2219 std::unique_ptr<Animation> animation( |
| 2220 Animation::Create(std::move(curve1), 2, 2, TargetProperty::TRANSFORM)); |
| 2221 animations_impl->AddAnimation(std::move(animation)); |
| 2222 |
| 2223 // Translations don't affect scale. |
| 2224 EXPECT_FALSE(animations_impl->HasAnimationThatAffectsScale()); |
| 2225 |
| 2226 std::unique_ptr<KeyframedTransformAnimationCurve> curve2( |
| 2227 KeyframedTransformAnimationCurve::Create()); |
| 2228 |
| 2229 TransformOperations operations2; |
| 2230 curve2->AddKeyframe( |
| 2231 TransformKeyframe::Create(base::TimeDelta(), operations2, nullptr)); |
| 2232 operations2.AppendScale(2.0, 3.0, 4.0); |
| 2233 curve2->AddKeyframe(TransformKeyframe::Create( |
| 2234 base::TimeDelta::FromSecondsD(1.0), operations2, nullptr)); |
| 2235 |
| 2236 animation = |
| 2237 Animation::Create(std::move(curve2), 3, 3, TargetProperty::TRANSFORM); |
| 2238 animations_impl->AddAnimation(std::move(animation)); |
| 2239 |
| 2240 EXPECT_TRUE(animations_impl->HasAnimationThatAffectsScale()); |
| 2241 |
| 2242 animations_impl->GetAnimationById(3)->SetRunState(Animation::FINISHED, |
| 2243 TicksFromSecondsF(0.0)); |
| 2244 |
| 2245 // Only unfinished animations should be considered by |
| 2246 // HasAnimationThatAffectsScale. |
| 2247 EXPECT_FALSE(animations_impl->HasAnimationThatAffectsScale()); |
| 2248 } |
| 2249 |
| 2250 TEST_F(ElementAnimationsTest, HasOnlyTranslationTransforms) { |
| 2251 CreateTestLayer(true, false); |
| 2252 AttachTimelinePlayerLayer(); |
| 2253 CreateImplTimelineAndPlayer(); |
| 2254 |
| 2255 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2256 |
| 2257 EXPECT_TRUE(animations_impl->HasOnlyTranslationTransforms( |
| 2258 ElementAnimations::ObserverType::ACTIVE)); |
| 2259 EXPECT_TRUE(animations_impl->HasOnlyTranslationTransforms( |
| 2260 ElementAnimations::ObserverType::PENDING)); |
| 2261 |
| 2262 animations_impl->AddAnimation(CreateAnimation( |
| 2263 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 2264 1, TargetProperty::OPACITY)); |
| 2265 |
| 2266 // Opacity animations aren't non-translation transforms. |
| 2267 EXPECT_TRUE(animations_impl->HasOnlyTranslationTransforms( |
| 2268 ElementAnimations::ObserverType::ACTIVE)); |
| 2269 EXPECT_TRUE(animations_impl->HasOnlyTranslationTransforms( |
| 2270 ElementAnimations::ObserverType::PENDING)); |
| 2271 |
| 2272 std::unique_ptr<KeyframedTransformAnimationCurve> curve1( |
| 2273 KeyframedTransformAnimationCurve::Create()); |
| 2274 |
| 2275 TransformOperations operations1; |
| 2276 curve1->AddKeyframe( |
| 2277 TransformKeyframe::Create(base::TimeDelta(), operations1, nullptr)); |
| 2278 operations1.AppendTranslate(10.0, 15.0, 0.0); |
| 2279 curve1->AddKeyframe(TransformKeyframe::Create( |
| 2280 base::TimeDelta::FromSecondsD(1.0), operations1, nullptr)); |
| 2281 |
| 2282 std::unique_ptr<Animation> animation( |
| 2283 Animation::Create(std::move(curve1), 2, 2, TargetProperty::TRANSFORM)); |
| 2284 animations_impl->AddAnimation(std::move(animation)); |
| 2285 |
| 2286 // The only transform animation we've added is a translation. |
| 2287 EXPECT_TRUE(animations_impl->HasOnlyTranslationTransforms( |
| 2288 ElementAnimations::ObserverType::ACTIVE)); |
| 2289 EXPECT_TRUE(animations_impl->HasOnlyTranslationTransforms( |
| 2290 ElementAnimations::ObserverType::PENDING)); |
| 2291 |
| 2292 std::unique_ptr<KeyframedTransformAnimationCurve> curve2( |
| 2293 KeyframedTransformAnimationCurve::Create()); |
| 2294 |
| 2295 TransformOperations operations2; |
| 2296 curve2->AddKeyframe( |
| 2297 TransformKeyframe::Create(base::TimeDelta(), operations2, nullptr)); |
| 2298 operations2.AppendScale(2.0, 3.0, 4.0); |
| 2299 curve2->AddKeyframe(TransformKeyframe::Create( |
| 2300 base::TimeDelta::FromSecondsD(1.0), operations2, nullptr)); |
| 2301 |
| 2302 animation = |
| 2303 Animation::Create(std::move(curve2), 3, 3, TargetProperty::TRANSFORM); |
| 2304 animation->set_affects_active_observers(false); |
| 2305 animations_impl->AddAnimation(std::move(animation)); |
| 2306 |
| 2307 // A scale animation is not a translation. |
| 2308 EXPECT_FALSE(animations_impl->HasOnlyTranslationTransforms( |
| 2309 ElementAnimations::ObserverType::PENDING)); |
| 2310 EXPECT_TRUE(animations_impl->HasOnlyTranslationTransforms( |
| 2311 ElementAnimations::ObserverType::ACTIVE)); |
| 2312 |
| 2313 animations_impl->ActivateAnimations(); |
| 2314 EXPECT_FALSE(animations_impl->HasOnlyTranslationTransforms( |
| 2315 ElementAnimations::ObserverType::PENDING)); |
| 2316 EXPECT_FALSE(animations_impl->HasOnlyTranslationTransforms( |
| 2317 ElementAnimations::ObserverType::ACTIVE)); |
| 2318 |
| 2319 animations_impl->GetAnimationById(3)->set_affects_pending_observers(false); |
| 2320 EXPECT_TRUE(animations_impl->HasOnlyTranslationTransforms( |
| 2321 ElementAnimations::ObserverType::PENDING)); |
| 2322 EXPECT_FALSE(animations_impl->HasOnlyTranslationTransforms( |
| 2323 ElementAnimations::ObserverType::ACTIVE)); |
| 2324 |
| 2325 animations_impl->GetAnimationById(3)->SetRunState(Animation::FINISHED, |
| 2326 TicksFromSecondsF(0.0)); |
| 2327 |
| 2328 // Only unfinished animations should be considered by |
| 2329 // HasOnlyTranslationTransforms. |
| 2330 EXPECT_TRUE(animations_impl->HasOnlyTranslationTransforms( |
| 2331 ElementAnimations::ObserverType::PENDING)); |
| 2332 EXPECT_TRUE(animations_impl->HasOnlyTranslationTransforms( |
| 2333 ElementAnimations::ObserverType::ACTIVE)); |
| 2334 } |
| 2335 |
| 2336 TEST_F(ElementAnimationsTest, AnimationStartScale) { |
| 2337 CreateTestLayer(true, false); |
| 2338 AttachTimelinePlayerLayer(); |
| 2339 CreateImplTimelineAndPlayer(); |
| 2340 |
| 2341 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2342 |
| 2343 std::unique_ptr<KeyframedTransformAnimationCurve> curve1( |
| 2344 KeyframedTransformAnimationCurve::Create()); |
| 2345 |
| 2346 TransformOperations operations1; |
| 2347 operations1.AppendScale(2.0, 3.0, 4.0); |
| 2348 curve1->AddKeyframe( |
| 2349 TransformKeyframe::Create(base::TimeDelta(), operations1, nullptr)); |
| 2350 TransformOperations operations2; |
| 2351 curve1->AddKeyframe(TransformKeyframe::Create( |
| 2352 base::TimeDelta::FromSecondsD(1.0), operations2, nullptr)); |
| 2353 std::unique_ptr<Animation> animation( |
| 2354 Animation::Create(std::move(curve1), 1, 1, TargetProperty::TRANSFORM)); |
| 2355 animation->set_affects_active_observers(false); |
| 2356 animations_impl->AddAnimation(std::move(animation)); |
| 2357 |
| 2358 float start_scale = 0.f; |
| 2359 EXPECT_TRUE(animations_impl->AnimationStartScale( |
| 2360 ElementAnimations::ObserverType::PENDING, &start_scale)); |
| 2361 EXPECT_EQ(4.f, start_scale); |
| 2362 EXPECT_TRUE(animations_impl->AnimationStartScale( |
| 2363 ElementAnimations::ObserverType::ACTIVE, &start_scale)); |
| 2364 EXPECT_EQ(0.f, start_scale); |
| 2365 |
| 2366 animations_impl->ActivateAnimations(); |
| 2367 EXPECT_TRUE(animations_impl->AnimationStartScale( |
| 2368 ElementAnimations::ObserverType::PENDING, &start_scale)); |
| 2369 EXPECT_EQ(4.f, start_scale); |
| 2370 EXPECT_TRUE(animations_impl->AnimationStartScale( |
| 2371 ElementAnimations::ObserverType::ACTIVE, &start_scale)); |
| 2372 EXPECT_EQ(4.f, start_scale); |
| 2373 |
| 2374 std::unique_ptr<KeyframedTransformAnimationCurve> curve2( |
| 2375 KeyframedTransformAnimationCurve::Create()); |
| 2376 |
| 2377 TransformOperations operations3; |
| 2378 curve2->AddKeyframe( |
| 2379 TransformKeyframe::Create(base::TimeDelta(), operations3, nullptr)); |
| 2380 operations3.AppendScale(6.0, 5.0, 4.0); |
| 2381 curve2->AddKeyframe(TransformKeyframe::Create( |
| 2382 base::TimeDelta::FromSecondsD(1.0), operations3, nullptr)); |
| 2383 |
| 2384 animations_impl->RemoveAnimation(1); |
| 2385 animation = |
| 2386 Animation::Create(std::move(curve2), 2, 2, TargetProperty::TRANSFORM); |
| 2387 |
| 2388 // Reverse Direction |
| 2389 animation->set_direction(Animation::DIRECTION_REVERSE); |
| 2390 animation->set_affects_active_observers(false); |
| 2391 animations_impl->AddAnimation(std::move(animation)); |
| 2392 |
| 2393 std::unique_ptr<KeyframedTransformAnimationCurve> curve3( |
| 2394 KeyframedTransformAnimationCurve::Create()); |
| 2395 |
| 2396 TransformOperations operations4; |
| 2397 operations4.AppendScale(5.0, 3.0, 1.0); |
| 2398 curve3->AddKeyframe( |
| 2399 TransformKeyframe::Create(base::TimeDelta(), operations4, nullptr)); |
| 2400 TransformOperations operations5; |
| 2401 curve3->AddKeyframe(TransformKeyframe::Create( |
| 2402 base::TimeDelta::FromSecondsD(1.0), operations5, nullptr)); |
| 2403 |
| 2404 animation = |
| 2405 Animation::Create(std::move(curve3), 3, 3, TargetProperty::TRANSFORM); |
| 2406 animation->set_affects_active_observers(false); |
| 2407 animations_impl->AddAnimation(std::move(animation)); |
| 2408 |
| 2409 EXPECT_TRUE(animations_impl->AnimationStartScale( |
| 2410 ElementAnimations::ObserverType::PENDING, &start_scale)); |
| 2411 EXPECT_EQ(6.f, start_scale); |
| 2412 EXPECT_TRUE(animations_impl->AnimationStartScale( |
| 2413 ElementAnimations::ObserverType::ACTIVE, &start_scale)); |
| 2414 EXPECT_EQ(0.f, start_scale); |
| 2415 |
| 2416 animations_impl->ActivateAnimations(); |
| 2417 EXPECT_TRUE(animations_impl->AnimationStartScale( |
| 2418 ElementAnimations::ObserverType::PENDING, &start_scale)); |
| 2419 EXPECT_EQ(6.f, start_scale); |
| 2420 EXPECT_TRUE(animations_impl->AnimationStartScale( |
| 2421 ElementAnimations::ObserverType::ACTIVE, &start_scale)); |
| 2422 EXPECT_EQ(6.f, start_scale); |
| 2423 |
| 2424 animations_impl->GetAnimationById(2)->SetRunState(Animation::FINISHED, |
| 2425 TicksFromSecondsF(0.0)); |
| 2426 |
| 2427 // Only unfinished animations should be considered by |
| 2428 // AnimationStartScale. |
| 2429 EXPECT_TRUE(animations_impl->AnimationStartScale( |
| 2430 ElementAnimations::ObserverType::PENDING, &start_scale)); |
| 2431 EXPECT_EQ(5.f, start_scale); |
| 2432 EXPECT_TRUE(animations_impl->AnimationStartScale( |
| 2433 ElementAnimations::ObserverType::ACTIVE, &start_scale)); |
| 2434 EXPECT_EQ(5.f, start_scale); |
| 2435 } |
| 2436 |
| 2437 TEST_F(ElementAnimationsTest, MaximumTargetScale) { |
| 2438 CreateTestLayer(true, false); |
| 2439 AttachTimelinePlayerLayer(); |
| 2440 CreateImplTimelineAndPlayer(); |
| 2441 |
| 2442 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2443 |
| 2444 float max_scale = 0.f; |
| 2445 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2446 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2447 EXPECT_EQ(0.f, max_scale); |
| 2448 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2449 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2450 EXPECT_EQ(0.f, max_scale); |
| 2451 |
| 2452 std::unique_ptr<KeyframedTransformAnimationCurve> curve1( |
| 2453 KeyframedTransformAnimationCurve::Create()); |
| 2454 |
| 2455 TransformOperations operations1; |
| 2456 curve1->AddKeyframe( |
| 2457 TransformKeyframe::Create(base::TimeDelta(), operations1, nullptr)); |
| 2458 operations1.AppendScale(2.0, 3.0, 4.0); |
| 2459 curve1->AddKeyframe(TransformKeyframe::Create( |
| 2460 base::TimeDelta::FromSecondsD(1.0), operations1, nullptr)); |
| 2461 |
| 2462 std::unique_ptr<Animation> animation( |
| 2463 Animation::Create(std::move(curve1), 1, 1, TargetProperty::TRANSFORM)); |
| 2464 animation->set_affects_active_observers(false); |
| 2465 animations_impl->AddAnimation(std::move(animation)); |
| 2466 |
| 2467 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2468 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2469 EXPECT_EQ(4.f, max_scale); |
| 2470 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2471 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2472 EXPECT_EQ(0.f, max_scale); |
| 2473 |
| 2474 animations_impl->ActivateAnimations(); |
| 2475 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2476 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2477 EXPECT_EQ(4.f, max_scale); |
| 2478 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2479 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2480 EXPECT_EQ(4.f, max_scale); |
| 2481 |
| 2482 std::unique_ptr<KeyframedTransformAnimationCurve> curve2( |
| 2483 KeyframedTransformAnimationCurve::Create()); |
| 2484 |
| 2485 TransformOperations operations2; |
| 2486 curve2->AddKeyframe( |
| 2487 TransformKeyframe::Create(base::TimeDelta(), operations2, nullptr)); |
| 2488 operations2.AppendScale(6.0, 5.0, 4.0); |
| 2489 curve2->AddKeyframe(TransformKeyframe::Create( |
| 2490 base::TimeDelta::FromSecondsD(1.0), operations2, nullptr)); |
| 2491 |
| 2492 animation = |
| 2493 Animation::Create(std::move(curve2), 2, 2, TargetProperty::TRANSFORM); |
| 2494 animation->set_affects_active_observers(false); |
| 2495 animations_impl->AddAnimation(std::move(animation)); |
| 2496 |
| 2497 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2498 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2499 EXPECT_EQ(6.f, max_scale); |
| 2500 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2501 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2502 EXPECT_EQ(4.f, max_scale); |
| 2503 |
| 2504 animations_impl->ActivateAnimations(); |
| 2505 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2506 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2507 EXPECT_EQ(6.f, max_scale); |
| 2508 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2509 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2510 EXPECT_EQ(6.f, max_scale); |
| 2511 |
| 2512 std::unique_ptr<KeyframedTransformAnimationCurve> curve3( |
| 2513 KeyframedTransformAnimationCurve::Create()); |
| 2514 |
| 2515 TransformOperations operations3; |
| 2516 curve3->AddKeyframe( |
| 2517 TransformKeyframe::Create(base::TimeDelta(), operations3, nullptr)); |
| 2518 operations3.AppendPerspective(6.0); |
| 2519 curve3->AddKeyframe(TransformKeyframe::Create( |
| 2520 base::TimeDelta::FromSecondsD(1.0), operations3, nullptr)); |
| 2521 |
| 2522 animation = |
| 2523 Animation::Create(std::move(curve3), 3, 3, TargetProperty::TRANSFORM); |
| 2524 animation->set_affects_active_observers(false); |
| 2525 animations_impl->AddAnimation(std::move(animation)); |
| 2526 |
| 2527 EXPECT_FALSE(animations_impl->MaximumTargetScale( |
| 2528 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2529 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2530 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2531 EXPECT_EQ(6.f, max_scale); |
| 2532 |
| 2533 animations_impl->ActivateAnimations(); |
| 2534 EXPECT_FALSE(animations_impl->MaximumTargetScale( |
| 2535 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2536 EXPECT_FALSE(animations_impl->MaximumTargetScale( |
| 2537 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2538 |
| 2539 animations_impl->GetAnimationById(3)->SetRunState(Animation::FINISHED, |
| 2540 TicksFromSecondsF(0.0)); |
| 2541 animations_impl->GetAnimationById(2)->SetRunState(Animation::FINISHED, |
| 2542 TicksFromSecondsF(0.0)); |
| 2543 |
| 2544 // Only unfinished animations should be considered by |
| 2545 // MaximumTargetScale. |
| 2546 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2547 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2548 EXPECT_EQ(4.f, max_scale); |
| 2549 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2550 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2551 EXPECT_EQ(4.f, max_scale); |
| 2552 } |
| 2553 |
| 2554 TEST_F(ElementAnimationsTest, MaximumTargetScaleWithDirection) { |
| 2555 CreateTestLayer(true, false); |
| 2556 AttachTimelinePlayerLayer(); |
| 2557 CreateImplTimelineAndPlayer(); |
| 2558 |
| 2559 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2560 |
| 2561 std::unique_ptr<KeyframedTransformAnimationCurve> curve1( |
| 2562 KeyframedTransformAnimationCurve::Create()); |
| 2563 TransformOperations operations1; |
| 2564 operations1.AppendScale(1.0, 2.0, 3.0); |
| 2565 curve1->AddKeyframe( |
| 2566 TransformKeyframe::Create(base::TimeDelta(), operations1, nullptr)); |
| 2567 TransformOperations operations2; |
| 2568 operations2.AppendScale(4.0, 5.0, 6.0); |
| 2569 curve1->AddKeyframe(TransformKeyframe::Create( |
| 2570 base::TimeDelta::FromSecondsD(1.0), operations2, nullptr)); |
| 2571 |
| 2572 std::unique_ptr<Animation> animation_owned( |
| 2573 Animation::Create(std::move(curve1), 1, 1, TargetProperty::TRANSFORM)); |
| 2574 Animation* animation = animation_owned.get(); |
| 2575 animations_impl->AddAnimation(std::move(animation_owned)); |
| 2576 |
| 2577 float max_scale = 0.f; |
| 2578 |
| 2579 EXPECT_GT(animation->playback_rate(), 0.0); |
| 2580 |
| 2581 // NORMAL direction with positive playback rate. |
| 2582 animation->set_direction(Animation::DIRECTION_NORMAL); |
| 2583 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2584 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2585 EXPECT_EQ(6.f, max_scale); |
| 2586 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2587 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2588 EXPECT_EQ(6.f, max_scale); |
| 2589 |
| 2590 // ALTERNATE direction with positive playback rate. |
| 2591 animation->set_direction(Animation::DIRECTION_ALTERNATE); |
| 2592 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2593 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2594 EXPECT_EQ(6.f, max_scale); |
| 2595 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2596 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2597 EXPECT_EQ(6.f, max_scale); |
| 2598 |
| 2599 // REVERSE direction with positive playback rate. |
| 2600 animation->set_direction(Animation::DIRECTION_REVERSE); |
| 2601 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2602 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2603 EXPECT_EQ(3.f, max_scale); |
| 2604 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2605 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2606 EXPECT_EQ(3.f, max_scale); |
| 2607 |
| 2608 // ALTERNATE reverse direction. |
| 2609 animation->set_direction(Animation::DIRECTION_REVERSE); |
| 2610 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2611 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2612 EXPECT_EQ(3.f, max_scale); |
| 2613 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2614 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2615 EXPECT_EQ(3.f, max_scale); |
| 2616 |
| 2617 animation->set_playback_rate(-1.0); |
| 2618 |
| 2619 // NORMAL direction with negative playback rate. |
| 2620 animation->set_direction(Animation::DIRECTION_NORMAL); |
| 2621 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2622 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2623 EXPECT_EQ(3.f, max_scale); |
| 2624 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2625 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2626 EXPECT_EQ(3.f, max_scale); |
| 2627 |
| 2628 // ALTERNATE direction with negative playback rate. |
| 2629 animation->set_direction(Animation::DIRECTION_ALTERNATE); |
| 2630 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2631 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2632 EXPECT_EQ(3.f, max_scale); |
| 2633 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2634 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2635 EXPECT_EQ(3.f, max_scale); |
| 2636 |
| 2637 // REVERSE direction with negative playback rate. |
| 2638 animation->set_direction(Animation::DIRECTION_REVERSE); |
| 2639 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2640 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2641 EXPECT_EQ(6.f, max_scale); |
| 2642 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2643 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2644 EXPECT_EQ(6.f, max_scale); |
| 2645 |
| 2646 // ALTERNATE reverse direction with negative playback rate. |
| 2647 animation->set_direction(Animation::DIRECTION_REVERSE); |
| 2648 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2649 ElementAnimations::ObserverType::PENDING, &max_scale)); |
| 2650 EXPECT_EQ(6.f, max_scale); |
| 2651 EXPECT_TRUE(animations_impl->MaximumTargetScale( |
| 2652 ElementAnimations::ObserverType::ACTIVE, &max_scale)); |
| 2653 EXPECT_EQ(6.f, max_scale); |
| 2654 } |
| 2655 |
| 2656 TEST_F(ElementAnimationsTest, NewlyPushedAnimationWaitsForActivation) { |
| 2657 CreateTestLayer(true, true); |
| 2658 AttachTimelinePlayerLayer(); |
| 2659 CreateImplTimelineAndPlayer(); |
| 2660 |
| 2661 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 2662 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2663 |
| 2664 auto events = host_impl_->CreateEvents(); |
| 2665 |
| 2666 EXPECT_FALSE(animations->needs_to_start_animations_for_testing()); |
| 2667 int animation_id = AddOpacityTransitionToElementAnimations( |
| 2668 animations.get(), 1, 0.5f, 1.f, false); |
| 2669 EXPECT_TRUE(animations->needs_to_start_animations_for_testing()); |
| 2670 |
| 2671 EXPECT_FALSE(animations_impl->needs_to_start_animations_for_testing()); |
| 2672 animations->PushPropertiesTo(animations_impl.get()); |
| 2673 EXPECT_TRUE(animations_impl->needs_to_start_animations_for_testing()); |
| 2674 |
| 2675 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id)); |
| 2676 EXPECT_EQ(Animation::WAITING_FOR_TARGET_AVAILABILITY, |
| 2677 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 2678 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id) |
| 2679 ->affects_pending_observers()); |
| 2680 EXPECT_FALSE(animations_impl->GetAnimationById(animation_id) |
| 2681 ->affects_active_observers()); |
| 2682 |
| 2683 animations_impl->Animate(kInitialTickTime); |
| 2684 EXPECT_FALSE(animations_impl->needs_to_start_animations_for_testing()); |
| 2685 animations_impl->UpdateState(true, events.get()); |
| 2686 |
| 2687 // Since the animation hasn't been activated, it should still be STARTING |
| 2688 // rather than RUNNING. |
| 2689 EXPECT_EQ(Animation::STARTING, |
| 2690 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 2691 |
| 2692 // Since the animation hasn't been activated, only the pending observer |
| 2693 // should have been ticked. |
| 2694 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 2695 EXPECT_EQ(0.f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 2696 |
| 2697 animations_impl->ActivateAnimations(); |
| 2698 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id) |
| 2699 ->affects_pending_observers()); |
| 2700 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id) |
| 2701 ->affects_active_observers()); |
| 2702 |
| 2703 animations_impl->Animate(kInitialTickTime + |
| 2704 TimeDelta::FromMilliseconds(1000)); |
| 2705 animations_impl->UpdateState(true, events.get()); |
| 2706 |
| 2707 // Since the animation has been activated, it should have reached the |
| 2708 // RUNNING state and the active observer should start to get ticked. |
| 2709 EXPECT_EQ(Animation::RUNNING, |
| 2710 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 2711 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 2712 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 2713 } |
| 2714 |
| 2715 TEST_F(ElementAnimationsTest, ActivationBetweenAnimateAndUpdateState) { |
| 2716 CreateTestLayer(true, true); |
| 2717 AttachTimelinePlayerLayer(); |
| 2718 CreateImplTimelineAndPlayer(); |
| 2719 |
| 2720 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 2721 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2722 |
| 2723 auto events = host_impl_->CreateEvents(); |
| 2724 |
| 2725 const int animation_id = AddOpacityTransitionToElementAnimations( |
| 2726 animations.get(), 1, 0.5f, 1.f, true); |
| 2727 |
| 2728 animations->PushPropertiesTo(animations_impl.get()); |
| 2729 |
| 2730 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id)); |
| 2731 EXPECT_EQ(Animation::WAITING_FOR_TARGET_AVAILABILITY, |
| 2732 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 2733 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id) |
| 2734 ->affects_pending_observers()); |
| 2735 EXPECT_FALSE(animations_impl->GetAnimationById(animation_id) |
| 2736 ->affects_active_observers()); |
| 2737 |
| 2738 animations_impl->Animate(kInitialTickTime); |
| 2739 |
| 2740 // Since the animation hasn't been activated, only the pending observer |
| 2741 // should have been ticked. |
| 2742 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 2743 EXPECT_EQ(0.f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 2744 |
| 2745 animations_impl->ActivateAnimations(); |
| 2746 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id) |
| 2747 ->affects_pending_observers()); |
| 2748 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id) |
| 2749 ->affects_active_observers()); |
| 2750 |
| 2751 animations_impl->UpdateState(true, events.get()); |
| 2752 |
| 2753 // Since the animation has been activated, it should have reached the |
| 2754 // RUNNING state. |
| 2755 EXPECT_EQ(Animation::RUNNING, |
| 2756 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 2757 |
| 2758 animations_impl->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 2759 |
| 2760 // Both observers should have been ticked. |
| 2761 EXPECT_EQ(0.75f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 2762 EXPECT_EQ(0.75f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 2763 } |
| 2764 |
| 2765 TEST_F(ElementAnimationsTest, |
| 2766 ObserverNotifiedWhenTransformIsPotentiallyAnimatingChanges) { |
| 2767 CreateTestLayer(true, true); |
| 2768 AttachTimelinePlayerLayer(); |
| 2769 CreateImplTimelineAndPlayer(); |
| 2770 |
| 2771 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 2772 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2773 |
| 2774 auto events = host_impl_->CreateEvents(); |
| 2775 |
| 2776 EXPECT_FALSE( |
| 2777 client_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2778 EXPECT_FALSE( |
| 2779 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2780 EXPECT_FALSE( |
| 2781 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2782 |
| 2783 // Case 1: An animation that's allowed to run until its finish point. |
| 2784 AddAnimatedTransformToElementAnimations(animations.get(), 1.0, 1, 1); |
| 2785 EXPECT_TRUE( |
| 2786 client_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2787 |
| 2788 animations->PushPropertiesTo(animations_impl.get()); |
| 2789 EXPECT_TRUE( |
| 2790 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2791 EXPECT_FALSE( |
| 2792 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2793 |
| 2794 animations_impl->ActivateAnimations(); |
| 2795 EXPECT_TRUE( |
| 2796 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2797 EXPECT_TRUE( |
| 2798 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2799 |
| 2800 animations_impl->Animate(kInitialTickTime); |
| 2801 animations_impl->UpdateState(true, events.get()); |
| 2802 |
| 2803 animations->NotifyAnimationStarted(events->events_[0]); |
| 2804 events->events_.clear(); |
| 2805 |
| 2806 // Finish the animation. |
| 2807 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 2808 animations->UpdateState(true, nullptr); |
| 2809 EXPECT_FALSE( |
| 2810 client_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2811 |
| 2812 animations->PushPropertiesTo(animations_impl.get()); |
| 2813 |
| 2814 // animations_impl hasn't yet ticked at/past the end of the animation. |
| 2815 EXPECT_TRUE( |
| 2816 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2817 EXPECT_TRUE( |
| 2818 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2819 |
| 2820 animations_impl->Animate(kInitialTickTime + |
| 2821 TimeDelta::FromMilliseconds(1000)); |
| 2822 animations_impl->UpdateState(true, events.get()); |
| 2823 EXPECT_FALSE( |
| 2824 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2825 EXPECT_FALSE( |
| 2826 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2827 |
| 2828 animations->NotifyAnimationFinished(events->events_[0]); |
| 2829 events->events_.clear(); |
| 2830 |
| 2831 // Case 2: An animation that's removed before it finishes. |
| 2832 int animation_id = |
| 2833 AddAnimatedTransformToElementAnimations(animations.get(), 10.0, 2, 2); |
| 2834 EXPECT_TRUE( |
| 2835 client_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2836 |
| 2837 animations->PushPropertiesTo(animations_impl.get()); |
| 2838 EXPECT_TRUE( |
| 2839 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2840 EXPECT_FALSE( |
| 2841 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2842 |
| 2843 animations_impl->ActivateAnimations(); |
| 2844 EXPECT_TRUE( |
| 2845 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2846 EXPECT_TRUE( |
| 2847 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2848 |
| 2849 animations_impl->Animate(kInitialTickTime + |
| 2850 TimeDelta::FromMilliseconds(2000)); |
| 2851 animations_impl->UpdateState(true, events.get()); |
| 2852 |
| 2853 animations->NotifyAnimationStarted(events->events_[0]); |
| 2854 events->events_.clear(); |
| 2855 |
| 2856 animations->RemoveAnimation(animation_id); |
| 2857 EXPECT_FALSE( |
| 2858 client_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2859 |
| 2860 animations->PushPropertiesTo(animations_impl.get()); |
| 2861 EXPECT_FALSE( |
| 2862 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2863 EXPECT_TRUE( |
| 2864 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2865 |
| 2866 animations_impl->ActivateAnimations(); |
| 2867 EXPECT_FALSE( |
| 2868 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2869 EXPECT_FALSE( |
| 2870 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2871 |
| 2872 // Case 3: An animation that's aborted before it finishes. |
| 2873 animation_id = |
| 2874 AddAnimatedTransformToElementAnimations(animations.get(), 10.0, 3, 3); |
| 2875 EXPECT_TRUE( |
| 2876 client_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2877 |
| 2878 animations->PushPropertiesTo(animations_impl.get()); |
| 2879 EXPECT_TRUE( |
| 2880 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2881 EXPECT_FALSE( |
| 2882 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2883 |
| 2884 animations_impl->ActivateAnimations(); |
| 2885 EXPECT_TRUE( |
| 2886 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2887 EXPECT_TRUE( |
| 2888 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2889 |
| 2890 animations_impl->Animate(kInitialTickTime + |
| 2891 TimeDelta::FromMilliseconds(3000)); |
| 2892 animations_impl->UpdateState(true, events.get()); |
| 2893 |
| 2894 animations->NotifyAnimationStarted(events->events_[0]); |
| 2895 events->events_.clear(); |
| 2896 |
| 2897 animations_impl->AbortAnimations(TargetProperty::TRANSFORM); |
| 2898 EXPECT_FALSE( |
| 2899 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::PENDING)); |
| 2900 EXPECT_FALSE( |
| 2901 client_impl_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2902 |
| 2903 animations_impl->Animate(kInitialTickTime + |
| 2904 TimeDelta::FromMilliseconds(4000)); |
| 2905 animations_impl->UpdateState(true, events.get()); |
| 2906 |
| 2907 animations->NotifyAnimationAborted(events->events_[0]); |
| 2908 EXPECT_FALSE( |
| 2909 client_.GetTransformIsAnimating(layer_id_, LayerTreeType::ACTIVE)); |
| 2910 } |
| 2911 |
| 2912 TEST_F(ElementAnimationsTest, ClippedOpacityValues) { |
| 2913 CreateTestLayer(false, false); |
| 2914 AttachTimelinePlayerLayer(); |
| 2915 |
| 2916 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 2917 |
| 2918 AddOpacityTransitionToElementAnimations(animations.get(), 1, 1.f, 2.f, true); |
| 2919 |
| 2920 animations->Animate(kInitialTickTime); |
| 2921 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 2922 |
| 2923 // Opacity values are clipped [0,1] |
| 2924 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 2925 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 2926 } |
| 2927 |
| 2928 TEST_F(ElementAnimationsTest, ClippedNegativeOpacityValues) { |
| 2929 CreateTestLayer(false, false); |
| 2930 AttachTimelinePlayerLayer(); |
| 2931 |
| 2932 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 2933 |
| 2934 AddOpacityTransitionToElementAnimations(animations.get(), 1, 0.f, -2.f, true); |
| 2935 |
| 2936 animations->Animate(kInitialTickTime); |
| 2937 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 2938 |
| 2939 // Opacity values are clipped [0,1] |
| 2940 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1000)); |
| 2941 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 2942 } |
| 2943 |
| 2944 TEST_F(ElementAnimationsTest, PushedDeletedAnimationWaitsForActivation) { |
| 2945 CreateTestLayer(true, true); |
| 2946 AttachTimelinePlayerLayer(); |
| 2947 CreateImplTimelineAndPlayer(); |
| 2948 |
| 2949 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 2950 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 2951 |
| 2952 auto events = host_impl_->CreateEvents(); |
| 2953 |
| 2954 const int animation_id = AddOpacityTransitionToElementAnimations( |
| 2955 animations.get(), 1, 0.5f, 1.f, true); |
| 2956 |
| 2957 animations->PushPropertiesTo(animations_impl.get()); |
| 2958 animations_impl->ActivateAnimations(); |
| 2959 animations_impl->Animate(kInitialTickTime); |
| 2960 animations_impl->UpdateState(true, events.get()); |
| 2961 EXPECT_EQ(Animation::RUNNING, |
| 2962 animations_impl->GetAnimationById(animation_id)->run_state()); |
| 2963 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 2964 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 2965 |
| 2966 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id) |
| 2967 ->affects_pending_observers()); |
| 2968 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id) |
| 2969 ->affects_active_observers()); |
| 2970 |
| 2971 // Delete the animation on the main-thread animations. |
| 2972 animations->RemoveAnimation( |
| 2973 animations->GetAnimation(TargetProperty::OPACITY)->id()); |
| 2974 animations->PushPropertiesTo(animations_impl.get()); |
| 2975 |
| 2976 // The animation should no longer affect pending observers. |
| 2977 EXPECT_FALSE(animations_impl->GetAnimationById(animation_id) |
| 2978 ->affects_pending_observers()); |
| 2979 EXPECT_TRUE(animations_impl->GetAnimationById(animation_id) |
| 2980 ->affects_active_observers()); |
| 2981 |
| 2982 animations_impl->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 2983 animations_impl->UpdateState(true, events.get()); |
| 2984 |
| 2985 // Only the active observer should have been ticked. |
| 2986 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 2987 EXPECT_EQ(0.75f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 2988 |
| 2989 animations_impl->ActivateAnimations(); |
| 2990 |
| 2991 // Activation should cause the animation to be deleted. |
| 2992 EXPECT_FALSE(animations_impl->has_any_animation()); |
| 2993 } |
| 2994 |
| 2995 // Tests that an animation that affects only active observers won't block |
| 2996 // an animation that affects only pending observers from starting. |
| 2997 TEST_F(ElementAnimationsTest, StartAnimationsAffectingDifferentObservers) { |
| 2998 CreateTestLayer(true, true); |
| 2999 AttachTimelinePlayerLayer(); |
| 3000 CreateImplTimelineAndPlayer(); |
| 3001 |
| 3002 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 3003 scoped_refptr<ElementAnimations> animations_impl = element_animations_impl(); |
| 3004 |
| 3005 auto events = host_impl_->CreateEvents(); |
| 3006 |
| 3007 const int first_animation_id = AddOpacityTransitionToElementAnimations( |
| 3008 animations.get(), 1, 0.f, 1.f, true); |
| 3009 |
| 3010 animations->PushPropertiesTo(animations_impl.get()); |
| 3011 animations_impl->ActivateAnimations(); |
| 3012 animations_impl->Animate(kInitialTickTime); |
| 3013 animations_impl->UpdateState(true, events.get()); |
| 3014 |
| 3015 // Remove the first animation from the main-thread animations, and add a |
| 3016 // new animation affecting the same property. |
| 3017 animations->RemoveAnimation( |
| 3018 animations->GetAnimation(TargetProperty::OPACITY)->id()); |
| 3019 const int second_animation_id = AddOpacityTransitionToElementAnimations( |
| 3020 animations.get(), 1, 1.f, 0.5f, true); |
| 3021 animations->PushPropertiesTo(animations_impl.get()); |
| 3022 |
| 3023 // The original animation should only affect active observers, and the new |
| 3024 // animation should only affect pending observers. |
| 3025 EXPECT_FALSE(animations_impl->GetAnimationById(first_animation_id) |
| 3026 ->affects_pending_observers()); |
| 3027 EXPECT_TRUE(animations_impl->GetAnimationById(first_animation_id) |
| 3028 ->affects_active_observers()); |
| 3029 EXPECT_TRUE(animations_impl->GetAnimationById(second_animation_id) |
| 3030 ->affects_pending_observers()); |
| 3031 EXPECT_FALSE(animations_impl->GetAnimationById(second_animation_id) |
| 3032 ->affects_active_observers()); |
| 3033 |
| 3034 animations_impl->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(500)); |
| 3035 animations_impl->UpdateState(true, events.get()); |
| 3036 |
| 3037 // The original animation should still be running, and the new animation |
| 3038 // should be starting. |
| 3039 EXPECT_EQ(Animation::RUNNING, |
| 3040 animations_impl->GetAnimationById(first_animation_id)->run_state()); |
| 3041 EXPECT_EQ( |
| 3042 Animation::STARTING, |
| 3043 animations_impl->GetAnimationById(second_animation_id)->run_state()); |
| 3044 |
| 3045 // The active observer should have been ticked by the original animation, |
| 3046 // and the pending observer should have been ticked by the new animation. |
| 3047 EXPECT_EQ(1.f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 3048 EXPECT_EQ(0.5f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 3049 |
| 3050 animations_impl->ActivateAnimations(); |
| 3051 |
| 3052 // The original animation should have been deleted, and the new animation |
| 3053 // should now affect both observers. |
| 3054 EXPECT_FALSE(animations_impl->GetAnimationById(first_animation_id)); |
| 3055 EXPECT_TRUE(animations_impl->GetAnimationById(second_animation_id) |
| 3056 ->affects_pending_observers()); |
| 3057 EXPECT_TRUE(animations_impl->GetAnimationById(second_animation_id) |
| 3058 ->affects_active_observers()); |
| 3059 |
| 3060 animations_impl->Animate(kInitialTickTime + |
| 3061 TimeDelta::FromMilliseconds(1000)); |
| 3062 animations_impl->UpdateState(true, events.get()); |
| 3063 |
| 3064 // The new animation should be running, and the active observer should have |
| 3065 // been ticked at the new animation's starting point. |
| 3066 EXPECT_EQ( |
| 3067 Animation::RUNNING, |
| 3068 animations_impl->GetAnimationById(second_animation_id)->run_state()); |
| 3069 EXPECT_EQ(1.f, client_impl_.GetOpacity(layer_id_, LayerTreeType::PENDING)); |
| 3070 EXPECT_EQ(1.f, client_impl_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 3071 } |
| 3072 |
| 3073 TEST_F(ElementAnimationsTest, TestIsCurrentlyAnimatingProperty) { |
| 3074 CreateTestLayer(false, false); |
| 3075 AttachTimelinePlayerLayer(); |
| 3076 |
| 3077 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 3078 |
| 3079 // Create an animation that initially affects only pending observers. |
| 3080 std::unique_ptr<Animation> animation(CreateAnimation( |
| 3081 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 3082 1, TargetProperty::OPACITY)); |
| 3083 animation->set_affects_active_observers(false); |
| 3084 |
| 3085 animations->AddAnimation(std::move(animation)); |
| 3086 animations->Animate(kInitialTickTime); |
| 3087 EXPECT_TRUE(animations->IsCurrentlyAnimatingProperty( |
| 3088 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3089 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3090 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3091 animations->UpdateState(true, nullptr); |
| 3092 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 3093 |
| 3094 EXPECT_TRUE(animations->IsCurrentlyAnimatingProperty( |
| 3095 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3096 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3097 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3098 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3099 TargetProperty::FILTER, ElementAnimations::ObserverType::PENDING)); |
| 3100 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3101 TargetProperty::FILTER, ElementAnimations::ObserverType::ACTIVE)); |
| 3102 |
| 3103 animations->ActivateAnimations(); |
| 3104 |
| 3105 EXPECT_TRUE(animations->IsCurrentlyAnimatingProperty( |
| 3106 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3107 EXPECT_TRUE(animations->IsCurrentlyAnimatingProperty( |
| 3108 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3109 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3110 TargetProperty::FILTER, ElementAnimations::ObserverType::PENDING)); |
| 3111 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3112 TargetProperty::FILTER, ElementAnimations::ObserverType::ACTIVE)); |
| 3113 |
| 3114 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(10)); |
| 3115 animations->UpdateState(true, nullptr); |
| 3116 |
| 3117 EXPECT_TRUE(animations->IsCurrentlyAnimatingProperty( |
| 3118 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3119 EXPECT_TRUE(animations->IsCurrentlyAnimatingProperty( |
| 3120 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3121 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3122 TargetProperty::FILTER, ElementAnimations::ObserverType::PENDING)); |
| 3123 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3124 TargetProperty::FILTER, ElementAnimations::ObserverType::ACTIVE)); |
| 3125 |
| 3126 EXPECT_EQ(0.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 3127 |
| 3128 // Tick past the end of the animation. |
| 3129 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(1100)); |
| 3130 animations->UpdateState(true, nullptr); |
| 3131 |
| 3132 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3133 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3134 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3135 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3136 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3137 TargetProperty::FILTER, ElementAnimations::ObserverType::PENDING)); |
| 3138 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3139 TargetProperty::FILTER, ElementAnimations::ObserverType::ACTIVE)); |
| 3140 |
| 3141 EXPECT_EQ(1.f, client_.GetOpacity(layer_id_, LayerTreeType::ACTIVE)); |
| 3142 } |
| 3143 |
| 3144 TEST_F(ElementAnimationsTest, TestIsAnimatingPropertyTimeOffsetFillMode) { |
| 3145 CreateTestLayer(false, false); |
| 3146 AttachTimelinePlayerLayer(); |
| 3147 |
| 3148 scoped_refptr<ElementAnimations> animations = element_animations(); |
| 3149 |
| 3150 // Create an animation that initially affects only pending observers, and has |
| 3151 // a start delay of 2 seconds. |
| 3152 std::unique_ptr<Animation> animation(CreateAnimation( |
| 3153 std::unique_ptr<AnimationCurve>(new FakeFloatTransition(1.0, 0.f, 1.f)), |
| 3154 1, TargetProperty::OPACITY)); |
| 3155 animation->set_fill_mode(Animation::FILL_MODE_NONE); |
| 3156 animation->set_time_offset(TimeDelta::FromMilliseconds(-2000)); |
| 3157 animation->set_affects_active_observers(false); |
| 3158 |
| 3159 animations->AddAnimation(std::move(animation)); |
| 3160 |
| 3161 animations->Animate(kInitialTickTime); |
| 3162 |
| 3163 // Since the animation has a start delay, the observers it affects have a |
| 3164 // potentially running transform animation but aren't currently animating |
| 3165 // transform. |
| 3166 EXPECT_TRUE(animations->IsPotentiallyAnimatingProperty( |
| 3167 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3168 EXPECT_FALSE(animations->IsPotentiallyAnimatingProperty( |
| 3169 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3170 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3171 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3172 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3173 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3174 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 3175 EXPECT_FALSE(animations->IsPotentiallyAnimatingProperty( |
| 3176 TargetProperty::FILTER, ElementAnimations::ObserverType::PENDING)); |
| 3177 EXPECT_FALSE(animations->IsPotentiallyAnimatingProperty( |
| 3178 TargetProperty::FILTER, ElementAnimations::ObserverType::ACTIVE)); |
| 3179 |
| 3180 animations->ActivateAnimations(); |
| 3181 |
| 3182 EXPECT_TRUE(animations->IsPotentiallyAnimatingProperty( |
| 3183 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3184 EXPECT_TRUE(animations->IsPotentiallyAnimatingProperty( |
| 3185 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3186 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3187 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3188 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3189 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3190 EXPECT_TRUE(animations->HasActiveAnimation()); |
| 3191 EXPECT_FALSE(animations->IsPotentiallyAnimatingProperty( |
| 3192 TargetProperty::FILTER, ElementAnimations::ObserverType::PENDING)); |
| 3193 EXPECT_FALSE(animations->IsPotentiallyAnimatingProperty( |
| 3194 TargetProperty::FILTER, ElementAnimations::ObserverType::ACTIVE)); |
| 3195 |
| 3196 animations->UpdateState(true, nullptr); |
| 3197 |
| 3198 // Tick past the start delay. |
| 3199 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(2000)); |
| 3200 animations->UpdateState(true, nullptr); |
| 3201 EXPECT_TRUE(animations->IsPotentiallyAnimatingProperty( |
| 3202 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3203 EXPECT_TRUE(animations->IsPotentiallyAnimatingProperty( |
| 3204 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3205 EXPECT_TRUE(animations->IsCurrentlyAnimatingProperty( |
| 3206 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3207 EXPECT_TRUE(animations->IsCurrentlyAnimatingProperty( |
| 3208 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3209 |
| 3210 // After the animaton finishes, the observers it affects have neither a |
| 3211 // potentially running transform animation nor a currently running transform |
| 3212 // animation. |
| 3213 animations->Animate(kInitialTickTime + TimeDelta::FromMilliseconds(4000)); |
| 3214 animations->UpdateState(true, nullptr); |
| 3215 EXPECT_FALSE(animations->IsPotentiallyAnimatingProperty( |
| 3216 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3217 EXPECT_FALSE(animations->IsPotentiallyAnimatingProperty( |
| 3218 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3219 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3220 TargetProperty::OPACITY, ElementAnimations::ObserverType::PENDING)); |
| 3221 EXPECT_FALSE(animations->IsCurrentlyAnimatingProperty( |
| 3222 TargetProperty::OPACITY, ElementAnimations::ObserverType::ACTIVE)); |
| 3223 } |
| 3224 |
| 205 } // namespace | 3225 } // namespace |
| 206 } // namespace cc | 3226 } // namespace cc |
| OLD | NEW |