1// Copyright (c) 2011 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "ui/gfx/animation/multi_animation.h"
6
7#include "testing/gtest/include/gtest/gtest.h"
8#include "ui/gfx/animation/animation_container_element.h"
9
10namespace gfx {
11
12TEST(MultiAnimationTest, Basic) {
13  // Create a MultiAnimation with two parts.
14  MultiAnimation::Parts parts;
15  parts.push_back(MultiAnimation::Part(100, Tween::LINEAR));
16  parts.push_back(MultiAnimation::Part(100, Tween::EASE_OUT));
17
18  MultiAnimation animation(parts, MultiAnimation::GetDefaultTimerInterval());
19  AnimationContainerElement* as_element =
20      static_cast<AnimationContainerElement*>(&animation);
21  as_element->SetStartTime(base::TimeTicks());
22
23  // Step to 50, which is half way through the first part.
24  as_element->Step(base::TimeTicks() + base::TimeDelta::FromMilliseconds(50));
25  EXPECT_EQ(.5, animation.GetCurrentValue());
26
27  // Step to 120, which is 20% through the second part.
28  as_element->Step(base::TimeTicks() +
29                   base::TimeDelta::FromMilliseconds(120));
30  EXPECT_DOUBLE_EQ(Tween::CalculateValue(Tween::EASE_OUT, .2),
31                   animation.GetCurrentValue());
32
33  // Step to 320, which is 20% through the second part.
34  as_element->Step(base::TimeTicks() +
35                   base::TimeDelta::FromMilliseconds(320));
36  EXPECT_DOUBLE_EQ(Tween::CalculateValue(Tween::EASE_OUT, .2),
37                   animation.GetCurrentValue());
38}
39
40TEST(MultiAnimationTest, DifferingStartAndEnd) {
41  // Create a MultiAnimation with two parts.
42  MultiAnimation::Parts parts;
43  parts.push_back(MultiAnimation::Part(200, Tween::LINEAR));
44  parts[0].start_time_ms = 100;
45  parts[0].end_time_ms = 400;
46
47  MultiAnimation animation(parts, MultiAnimation::GetDefaultTimerInterval());
48  AnimationContainerElement* as_element =
49      static_cast<AnimationContainerElement*>(&animation);
50  as_element->SetStartTime(base::TimeTicks());
51
52  // Step to 0. Because the start_time is 100, this should be 100ms into the
53  // animation
54  as_element->Step(base::TimeTicks());
55  EXPECT_EQ(.25, animation.GetCurrentValue());
56
57  // Step to 100, which is effectively 200ms into the animation.
58  as_element->Step(base::TimeTicks() + base::TimeDelta::FromMilliseconds(100));
59  EXPECT_EQ(.5, animation.GetCurrentValue());
60}
61
62// Makes sure multi-animation stops if cycles is false.
63TEST(MultiAnimationTest, DontCycle) {
64  MultiAnimation::Parts parts;
65  parts.push_back(MultiAnimation::Part(200, Tween::LINEAR));
66  MultiAnimation animation(parts, MultiAnimation::GetDefaultTimerInterval());
67  AnimationContainerElement* as_element =
68      static_cast<AnimationContainerElement*>(&animation);
69  as_element->SetStartTime(base::TimeTicks());
70  animation.set_continuous(false);
71
72  // Step to 300, which is greater than the cycle time.
73  as_element->Step(base::TimeTicks() + base::TimeDelta::FromMilliseconds(300));
74  EXPECT_EQ(1.0, animation.GetCurrentValue());
75  EXPECT_FALSE(animation.is_animating());
76}
77
78// Makes sure multi-animation cycles correctly.
79TEST(MultiAnimationTest, Cycle) {
80  MultiAnimation::Parts parts;
81  parts.push_back(MultiAnimation::Part(200, Tween::LINEAR));
82  MultiAnimation animation(parts, MultiAnimation::GetDefaultTimerInterval());
83  AnimationContainerElement* as_element =
84      static_cast<AnimationContainerElement*>(&animation);
85  as_element->SetStartTime(base::TimeTicks());
86
87  // Step to 300, which is greater than the cycle time.
88  as_element->Step(base::TimeTicks() + base::TimeDelta::FromMilliseconds(300));
89  EXPECT_EQ(.5, animation.GetCurrentValue());
90}
91
92}  // namespace gfx
93