15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifndef UI_COMPOSITOR_LAYER_ANIMATION_SEQUENCE_H_ 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define UI_COMPOSITOR_LAYER_ANIMATION_SEQUENCE_H_ 75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <vector> 95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/gtest_prod_util.h" 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/memory/linked_ptr.h" 125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/memory/weak_ptr.h" 135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/observer_list.h" 14eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch#include "base/time/time.h" 155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/compositor/compositor_export.h" 165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ui/compositor/layer_animation_element.h" 175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace ui { 195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class LayerAnimationDelegate; 215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class LayerAnimationObserver; 225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Contains a collection of layer animation elements to be played one after 245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// another. Although it has a similar interface to LayerAnimationElement, it is 255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// not a LayerAnimationElement (i.e., it is not permitted to have a sequence in 265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// a sequence). Sequences own their elements, and sequences are themselves owned 275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// by a LayerAnimator. 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// 295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// TODO(vollick) Create a 'blended' sequence for transitioning between 305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// sequences. 315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// TODO(vollick) Eventually, the LayerAnimator will switch to a model where new 325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// work is scheduled rather than calling methods directly. This should make it 335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// impossible for temporary pointers to running animations to go stale. When 345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// this happens, there will be no need for LayerAnimationSequences to support 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// weak pointers. 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class COMPOSITOR_EXPORT LayerAnimationSequence 375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : public base::SupportsWeakPtr<LayerAnimationSequence> { 385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) LayerAnimationSequence(); 405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Takes ownership of the given element and adds it to the sequence. 415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) explicit LayerAnimationSequence(LayerAnimationElement* element); 425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual ~LayerAnimationSequence(); 435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Sets the start time for the animation. This must be called before the 452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // first call to {Start, IsFinished}. Once the animation is finished, this 462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // must be called again in order to restart the animation. 472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void set_start_time(base::TimeTicks start_time) { start_time_ = start_time; } 482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeTicks start_time() const { return start_time_; } 492a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 502a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Sets a flag indicating that this sequence will start together with other 512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // sequences, and at least one of the sequences in this group has a threaded 522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // first element. 532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void set_waiting_for_group_start(bool waiting) { 542a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) waiting_for_group_start_ = waiting; 552a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 562a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) bool waiting_for_group_start() { return waiting_for_group_start_; } 572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // This must be called before the first call to Progress. If starting the 592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // animation involves dispatching to another thread, then this will proceed 602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // with that dispatch, ultimately resulting in the animation getting an 612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // effective start time (the time the animation starts on the other thread). 622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void Start(LayerAnimationDelegate* delegate); 632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Updates the delegate to the appropriate value for |now|. Requests a 652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // redraw if it is required. 662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void Progress(base::TimeTicks now, LayerAnimationDelegate* delegate); 672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Returns true if calling Progress now, with the given time, will finish 692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // the animation. 702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) bool IsFinished(base::TimeTicks time); 712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Updates the delegate to the end of the animation; if this sequence is 732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // cyclic, updates the delegate to the end of one cycle of the sequence. 742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void ProgressToEnd(LayerAnimationDelegate* delegate); 755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Sets the target value to the value that would have been set had 775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // the sequence completed. Does nothing if the sequence is cyclic. 785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void GetTargetValue(LayerAnimationElement::TargetValue* target) const; 795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Aborts the given animation. 812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void Abort(LayerAnimationDelegate* delegate); 825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // All properties modified by the sequence. 845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const LayerAnimationElement::AnimatableProperties& properties() const { 855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return properties_; 865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Adds an element to the sequence. The sequences takes ownership of this 895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // element. 905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void AddElement(LayerAnimationElement* element); 915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Sequences can be looped indefinitely. 935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void set_is_cyclic(bool is_cyclic) { is_cyclic_ = is_cyclic; } 945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool is_cyclic() const { return is_cyclic_; } 955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Returns true if this sequence has at least one element conflicting with a 975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // property in |other|. 982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) bool HasConflictingProperty( 995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const LayerAnimationElement::AnimatableProperties& other) const; 1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1012a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Returns true if the first element animates on the compositor thread. 1022a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) bool IsFirstElementThreaded() const; 1032a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Used to identify groups of sequences that are supposed to start together. 1052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) int animation_group_id() const { return animation_group_id_; } 1062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void set_animation_group_id(int id) { animation_group_id_ = id; } 1072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // These functions are used for adding or removing observers from the observer 1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // list. The observers are notified when animations end. 1105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void AddObserver(LayerAnimationObserver* observer); 1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void RemoveObserver(LayerAnimationObserver* observer); 1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Called when a threaded animation is actually started. 1142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void OnThreadedAnimationStarted(const cc::AnimationEvent& event); 1152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Called when the animator schedules this sequence. 1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void OnScheduled(); 1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Called when the animator is destroyed. 1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void OnAnimatorDestroyed(); 1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // The last_progressed_fraction of the element most recently progressed by 1232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // by this sequence. Returns 0.0 if no elements have been progressed. 1242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) double last_progressed_fraction() const { return last_progressed_fraction_; } 1252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 1272a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) friend class LayerAnimatorTestController; 1282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) typedef std::vector<linked_ptr<LayerAnimationElement> > Elements; 1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) FRIEND_TEST_ALL_PREFIXES(LayerAnimatorTest, 1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ObserverReleasedBeforeAnimationSequenceEnds); 1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Notifies the observers that this sequence has been scheduled. 1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void NotifyScheduled(); 1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Notifies the observers that this sequence has ended. 1385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void NotifyEnded(); 1395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Notifies the observers that this sequence has been aborted. 1415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void NotifyAborted(); 1425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1432a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // The currently animating element. 1442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) LayerAnimationElement* CurrentElement(); 1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // The union of all the properties modified by all elements in the sequence. 1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) LayerAnimationElement::AnimatableProperties properties_; 1485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // The elements in the sequence. 1505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) Elements elements_; 1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // True if the sequence should be looped forever. 1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool is_cyclic_; 1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // These are used when animating to efficiently find the next element. 1565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) size_t last_element_; 1572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeTicks last_start_; 1582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // The start time of the current run of the sequence. 1602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeTicks start_time_; 1612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // True if this sequence will start together with other sequences, and at 1632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // least one of the sequences in this group has a threaded first element. 1642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) bool waiting_for_group_start_; 1652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Identifies groups of sequences that are supposed to start together. 1672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) int animation_group_id_; 1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // These parties are notified when layer animations end. 1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ObserverList<LayerAnimationObserver> observers_; 1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Tracks the last_progressed_fraction() of the most recently progressed 1732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // element. 1742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) double last_progressed_fraction_; 1752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(LayerAnimationSequence); 1775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 1785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace ui 1805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif // UI_COMPOSITOR_LAYER_ANIMATION_SEQUENCE_H_ 182