// Copyright 2014 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "ios/chrome/browser/ui/reversed_animation.h"

#import <QuartzCore/QuartzCore.h>
#include <algorithm>
#include <cmath>

#include "base/logging.h"
#include "base/mac/objc_property_releaser.h"

@protocol ReversedAnimationProtocol;
typedef CAAnimation<ReversedAnimationProtocol> ReversedAnimation;

namespace {
// Enum type used to denote the direction of a reversed animation relative to
// the original animation's direction.
typedef enum {
  ANIMATION_DIRECTION_NORMAL,
  ANIMATION_DIRECTION_REVERSE
} AnimationDirection;
// Returns the AnimationDirection opposite of |direction|.
AnimationDirection AnimationDirectionOpposite(AnimationDirection direction) {
  return direction == ANIMATION_DIRECTION_NORMAL ? ANIMATION_DIRECTION_REVERSE
                                                 : ANIMATION_DIRECTION_NORMAL;
}
}  // namespace

// Returns an animation that reverses |animation| when added to |layer|, given
// that |animation| is in |parent|'s timespace, which begins at
// |parentBeginTime|.
CAAnimation* CAAnimationMakeReverse(CAAnimation* animation,
                                    CALayer* layer,
                                    CAAnimationGroup* parent,
                                    CFTimeInterval parentBeginTime);
// Updates |reversedAnimation|'s properties for |animationToReverse|, given that
// |animationToReverse| is in |parent|'s timespace, which begins at
// |parentBeginTime|.
void UpdateReversedAnimation(ReversedAnimation* reversedAnimation,
                             CAAnimation* animationToReverse,
                             CALayer* layer,
                             CAAnimationGroup* parent,
                             CFTimeInterval parentBeginTime);

#pragma mark - ReversedAnimation protocol

@protocol ReversedAnimationProtocol<NSObject>

// The original animation that's being played in reverse.
@property(nonatomic, retain) CAAnimation* originalAnimation;
// The current direction for the animation.
@property(nonatomic, assign) AnimationDirection animationDirection;
// The offset into the original animation's duration at the begining of the
// reverse animation.
@property(nonatomic, assign) CFTimeInterval animationTimeOffset;

@end

#pragma mark - ReversedBasicAnimation

@interface ReversedBasicAnimation
    : CABasicAnimation<ReversedAnimationProtocol> {
  base::mac::ObjCPropertyReleaser _propertyReleaser_ReversedBasicAnimation;
}

// Returns an animation that performs |animation| in reverse when added to
// |layer|.  |parentBeginTime| should be set to the beginTime in absolute time
// of |animation|'s parent in the timing hierarchy.
+ (instancetype)reversedAnimationForAnimation:(CABasicAnimation*)animation
                                     forLayer:(CALayer*)layer
                                       parent:(CAAnimationGroup*)parent
                              parentBeginTime:(CFTimeInterval)parentBeginTime;

@end

@implementation ReversedBasicAnimation

@synthesize originalAnimation = _originalAnimation;
@synthesize animationDirection = _animationDirection;
@synthesize animationTimeOffset = _animationTimeOffset;

- (instancetype)init {
  self = [super init];
  if (self) {
    _propertyReleaser_ReversedBasicAnimation.Init(
        self, [ReversedBasicAnimation class]);
  }
  return self;
}

- (instancetype)copyWithZone:(NSZone*)zone {
  ReversedBasicAnimation* copy = [super copyWithZone:zone];
  copy.originalAnimation = self.originalAnimation;
  copy.animationDirection = self.animationDirection;
  copy.animationTimeOffset = self.animationTimeOffset;
  return copy;
}

+ (instancetype)reversedAnimationForAnimation:(CABasicAnimation*)animation
                                     forLayer:(CALayer*)layer
                                       parent:(CAAnimationGroup*)parent
                              parentBeginTime:(CFTimeInterval)parentBeginTime {
  // Create new animation and copy properties.  Note that we can't use |-copy|
  // because we need the new animation to be the correct class.
  NSString* keyPath = animation.keyPath;
  CFTimeInterval now =
      [layer convertTime:CACurrentMediaTime() fromLayer:nil] - parentBeginTime;
  ReversedBasicAnimation* reversedAnimation =
      [ReversedBasicAnimation animationWithKeyPath:keyPath];
  UpdateReversedAnimation(reversedAnimation, animation, layer, parent,
                          parentBeginTime);

  // Update from and to values.
  BOOL isReversed =
      reversedAnimation.animationDirection == ANIMATION_DIRECTION_REVERSE;
  CABasicAnimation* originalBasicAnimation =
      static_cast<CABasicAnimation*>(reversedAnimation.originalAnimation);
  reversedAnimation.toValue = isReversed ? originalBasicAnimation.fromValue
                                         : originalBasicAnimation.toValue;
  if (now > animation.beginTime &&
      now < animation.beginTime + animation.duration) {
    // Use the presentation layer's current value for reversals that occur mid-
    // animation.
    reversedAnimation.fromValue =
        [[layer presentationLayer] valueForKeyPath:keyPath];
  } else {
    reversedAnimation.fromValue = isReversed ? originalBasicAnimation.toValue
                                             : originalBasicAnimation.fromValue;
  }
  return reversedAnimation;
}

@end

#pragma mark - ReversedAnimationGroup

@interface ReversedAnimationGroup
    : CAAnimationGroup<ReversedAnimationProtocol> {
  base::mac::ObjCPropertyReleaser _propertyReleaser_ReversedAnimationGroup;
}

// Returns an animation that performs |animation| in reverse when added to
// |layer|.  |parentBeginTime| should be set to the beginTime in absolute time
// of the animation group to which |animation| belongs.
+ (instancetype)reversedAnimationGroupForGroup:(CAAnimationGroup*)group
                                      forLayer:(CALayer*)layer
                                        parent:(CAAnimationGroup*)parent
                               parentBeginTime:(CFTimeInterval)parentBeginTime;

@end

@implementation ReversedAnimationGroup

@synthesize originalAnimation = _originalAnimation;
@synthesize animationDirection = _animationDirection;
@synthesize animationTimeOffset = _animationTimeOffset;

- (instancetype)init {
  self = [super init];
  if (self) {
    _propertyReleaser_ReversedAnimationGroup.Init(
        self, [ReversedAnimationGroup class]);
  }
  return self;
}

- (instancetype)copyWithZone:(NSZone*)zone {
  ReversedAnimationGroup* copy = [super copyWithZone:zone];
  copy.originalAnimation = self.originalAnimation;
  copy.animationDirection = self.animationDirection;
  copy.animationTimeOffset = self.animationTimeOffset;
  return copy;
}

+ (instancetype)reversedAnimationGroupForGroup:(CAAnimationGroup*)group
                                      forLayer:(CALayer*)layer
                                        parent:(CAAnimationGroup*)parent
                               parentBeginTime:(CFTimeInterval)parentBeginTime {
  // Create new animation and copy properties.  Note that we can't use |-copy|
  // because we need the new animation to be the correct class.
  ReversedAnimationGroup* reversedGroup = [ReversedAnimationGroup animation];
  UpdateReversedAnimation(reversedGroup, group, layer, parent, parentBeginTime);

  // Reverse the animations of the original group.
  NSMutableArray* reversedAnimations = [NSMutableArray array];
  for (CAAnimation* animation in group.animations) {
    CAAnimation* reversedAnimation = CAAnimationMakeReverse(
        animation, layer, group, group.beginTime + parentBeginTime);
    [reversedAnimations addObject:reversedAnimation];
  }
  reversedGroup.animations = reversedAnimations;

  return reversedGroup;
}

@end

#pragma mark - animation_util functions

CAAnimation* CAAnimationMakeReverse(CAAnimation* animation, CALayer* layer) {
  return CAAnimationMakeReverse(animation, layer, nil, layer.beginTime);
}

CAAnimation* CAAnimationMakeReverse(CAAnimation* animation,
                                    CALayer* layer,
                                    CAAnimationGroup* parent,
                                    CFTimeInterval parentBeginTime) {
  CAAnimation* reversedAnimation = nil;
  if ([animation isKindOfClass:[CABasicAnimation class]]) {
    CABasicAnimation* basicAnimation =
        static_cast<CABasicAnimation*>(animation);
    reversedAnimation =
        [ReversedBasicAnimation reversedAnimationForAnimation:basicAnimation
                                                     forLayer:layer
                                                       parent:parent
                                              parentBeginTime:parentBeginTime];
  } else if ([animation isKindOfClass:[CAAnimationGroup class]]) {
    CAAnimationGroup* animationGroup =
        static_cast<CAAnimationGroup*>(animation);
    reversedAnimation =
        [ReversedAnimationGroup reversedAnimationGroupForGroup:animationGroup
                                                      forLayer:layer
                                                        parent:parent
                                               parentBeginTime:parentBeginTime];
  } else {
    // TODO(crbug.com/546202): Investigate possible general-case reversals.  It
    // may be possible to implement this by manipulating the CAMediaTiming
    // properties.
  }
  return reversedAnimation;
}

void UpdateReversedAnimation(ReversedAnimation* reversedAnimation,
                             CAAnimation* animationToReverse,
                             CALayer* layer,
                             CAAnimationGroup* parent,
                             CFTimeInterval parentBeginTime) {
  // Copy properties.
  CFTimeInterval now =
      [layer convertTime:CACurrentMediaTime() fromLayer:nil] - parentBeginTime;
  reversedAnimation.fillMode = animationToReverse.fillMode;
  reversedAnimation.removedOnCompletion =
      animationToReverse.removedOnCompletion;
  reversedAnimation.timingFunction = animationToReverse.timingFunction;

  // Extract the previous reversal if it exists.
  ReversedAnimation* previousReversedAnimation = nil;
  Protocol* reversedAnimationProtocol = @protocol(ReversedAnimationProtocol);
  if ([animationToReverse conformsToProtocol:reversedAnimationProtocol]) {
    previousReversedAnimation =
        static_cast<ReversedAnimation*>(animationToReverse);
    animationToReverse = previousReversedAnimation.originalAnimation;
  }
  reversedAnimation.originalAnimation = animationToReverse;
  reversedAnimation.animationDirection =
      previousReversedAnimation
          ? AnimationDirectionOpposite(
                previousReversedAnimation.animationDirection)
          : ANIMATION_DIRECTION_REVERSE;

  CAAnimation* previousAnimation = previousReversedAnimation
                                       ? previousReversedAnimation
                                       : animationToReverse;
  BOOL isReversed =
      reversedAnimation.animationDirection == ANIMATION_DIRECTION_REVERSE;
  if (now < previousAnimation.beginTime) {
    // Reversal occurs before previous animation begins.
    reversedAnimation.beginTime = 2.0 * now - previousAnimation.beginTime -
                                  reversedAnimation.originalAnimation.duration;
    reversedAnimation.duration = reversedAnimation.originalAnimation.duration;
    reversedAnimation.animationTimeOffset =
        isReversed ? 0 : reversedAnimation.originalAnimation.duration;
  } else if (now < previousAnimation.beginTime + previousAnimation.duration) {
    // Reversal occurs while the previous animation is occurring.
    reversedAnimation.beginTime = 0;
    CFTimeInterval timeDelta = now - previousAnimation.beginTime;
    reversedAnimation.animationTimeOffset =
        previousReversedAnimation.animationTimeOffset +
        (isReversed ? 1.0 : -1.0) * timeDelta;
    reversedAnimation.duration =
        isReversed ? reversedAnimation.animationTimeOffset
                   : reversedAnimation.originalAnimation.duration -
                         reversedAnimation.animationTimeOffset;
  } else {
    // Reversal occurs after the previous animation has ended.
    if (!parentBeginTime) {
      // If the parent's begin time is zero, the animation is using absolute
      // time as its beginTime.
      reversedAnimation.beginTime =
          2.0 * now - previousAnimation.beginTime - previousAnimation.duration;
    } else {
      CFTimeInterval previousEndTime =
          previousAnimation.beginTime + previousAnimation.duration;
      if (now > parent.duration) {
        // The animation's parent has already ended, so use the difference
        // between the parent's ending and the previous animation's end.
        reversedAnimation.beginTime = parent.duration - previousEndTime;
      } else {
        // The parent hasn't ended, so use the difference between the current
        // time and the previous animation's end.
        reversedAnimation.beginTime = now - previousEndTime;
      }
    }
    reversedAnimation.duration = reversedAnimation.originalAnimation.duration;
    reversedAnimation.animationTimeOffset =
        isReversed ? reversedAnimation.originalAnimation.duration : 0;
  }
}

void ReverseAnimationsForKeyForLayers(NSString* key, NSArray* layers) {
  for (CALayer* layer in layers) {
    CAAnimation* reversedAnimation =
        CAAnimationMakeReverse([layer animationForKey:key], layer);
    [layer removeAnimationForKey:key];
    [layer addAnimation:reversedAnimation forKey:key];
  }
}
