/*
 * Copyright 2015 Google Inc. All Rights Reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#include "cobalt/dom/css_animations_adapter.h"

#include <vector>

#include "cobalt/base/tokens.h"
#include "cobalt/cssom/css_declared_style_data.h"
#include "cobalt/cssom/css_keyframes_rule.h"
#include "cobalt/cssom/property_definitions.h"
#include "cobalt/cssom/timing_function_list_value.h"
#include "cobalt/dom/animation_event.h"
#include "cobalt/dom/dom_animatable.h"
#include "cobalt/web_animations/keyframe.h"
#include "cobalt/web_animations/keyframe_effect_read_only.h"

namespace cobalt {
namespace dom {

CSSAnimationsAdapter::CSSAnimationsAdapter(
    const scoped_refptr<dom::DOMAnimatable>& target)
    : animatable_(target) {}

CSSAnimationsAdapter::~CSSAnimationsAdapter() {
  for (AnimationMap::iterator iter = animation_map_.begin();
       iter != animation_map_.end(); ++iter) {
    delete iter->second;
  }
}

namespace {
// Convert a cssom::Animation::FillMode enum value to a
// web_animations::AnimationEffectTimingReadOnly::FillMode value.
web_animations::AnimationEffectTimingReadOnly::FillMode CSSToWebFillMode(
    cssom::Animation::FillMode css_fill_mode) {
  switch (css_fill_mode) {
    case cssom::Animation::kNone:
      return web_animations::AnimationEffectTimingReadOnly::kNone;
    case cssom::Animation::kForwards:
      return web_animations::AnimationEffectTimingReadOnly::kForwards;
    case cssom::Animation::kBackwards:
      return web_animations::AnimationEffectTimingReadOnly::kBackwards;
    case cssom::Animation::kBoth:
      return web_animations::AnimationEffectTimingReadOnly::kBoth;
  }

  NOTREACHED();
  return web_animations::AnimationEffectTimingReadOnly::kNone;
}

// Convert a cssom::Animation::PlaybackDirection enum value to a
// web_animations::AnimationEffectTimingReadOnly::PlaybackDirection value.
web_animations::AnimationEffectTimingReadOnly::PlaybackDirection
CSSToWebDirection(cssom::Animation::PlaybackDirection css_direction) {
  switch (css_direction) {
    case cssom::Animation::kNormal:
      return web_animations::AnimationEffectTimingReadOnly::kNormal;
    case cssom::Animation::kReverse:
      return web_animations::AnimationEffectTimingReadOnly::kReverse;
    case cssom::Animation::kAlternate:
      return web_animations::AnimationEffectTimingReadOnly::kAlternate;
    case cssom::Animation::kAlternateReverse:
      return web_animations::AnimationEffectTimingReadOnly::kAlternateReverse;
  }

  NOTREACHED();
  return web_animations::AnimationEffectTimingReadOnly::kNormal;
}

scoped_refptr<cssom::TimingFunction> GetTimingFunctionFromKeyframePropertyValue(
    const scoped_refptr<cssom::PropertyValue>& value) {
  // An 'animation-timing-function' specified as a property value in a keyframe
  // means that we should use the first value (since animation-timing-function
  // is a list) as the keyframe's timing function.
  return base::polymorphic_downcast<cssom::TimingFunctionListValue*>(
             value.get())
      ->value()[0];
}

std::vector<web_animations::Keyframe::Data>
ConvertCSSKeyframesToWebAnimationsKeyframes(
    const cssom::CSSKeyframesRule& keyframes,
    const scoped_refptr<cssom::TimingFunction>& default_timing_function) {
  // https://drafts.csswg.org/date/2015-03-02/web-animations-css-integration/#conversion-of-css-keyframes
  const std::vector<cssom::CSSKeyframesRule::KeyframeInfo>&
      sorted_css_keyframes = keyframes.sorted_keyframes();

  // 1. Initialize an empty list keyframeList.
  std::vector<web_animations::Keyframe::Data> keyframe_list;
  if (sorted_css_keyframes.empty()) {
    return keyframe_list;
  }
  keyframe_list.reserve(sorted_css_keyframes.size());

  // 2. For each keyframe in keyframes:
  for (size_t i = 0; i < sorted_css_keyframes.size(); ++i) {
    const cssom::CSSKeyframesRule::KeyframeInfo& keyframe(
        sorted_css_keyframes[i]);

    // 2.1. Create a new dictionary newKeyframe.
    // 2.2. Set newKeyframe's offset to the offset defined by keyframe.
    web_animations::Keyframe::Data new_keyframe(keyframe.offset);
    bool easing_was_set = false;
    // 2.4. For each property defined in keyframe:
    for (cssom::CSSDeclaredStyleData::PropertyValues::const_iterator iter =
             keyframe.style->declared_property_values().begin();
         iter != keyframe.style->declared_property_values().end(); ++iter) {
      // 2.3. If keyframe defines an animation-timing-function, set
      //      newKeyframe's easing to the defined animation-timing-function.
      if (iter->first == cssom::kAnimationTimingFunctionProperty) {
        new_keyframe.set_easing(
            GetTimingFunctionFromKeyframePropertyValue(iter->second));
        easing_was_set = true;
      } else {
        // 2.4.1. Set newKeyframe[property] to the value associated with that
        //        property in keyframe
        new_keyframe.AddPropertyValue(iter->first, iter->second);
      }
    }

    if (!easing_was_set) {
      // If no keyframe-specific easing was specified, use the animation's
      // default easing value for this keyframe.
      new_keyframe.set_easing(default_timing_function);
    }

    // 3. Add newKeyframe to keyframeList.
    keyframe_list.push_back(new_keyframe);
  }

  return keyframe_list;
}
}  // namespace

void CSSAnimationsAdapter::OnAnimationStarted(
    const cssom::Animation& css_animation) {
  // The process for constructing web animations from CSS animations is
  // specified here:
  //   https://drafts.csswg.org/date/2015-03-02/web-animations-css-integration/#css-animations

  // Transfer the CSS Animation timing information into a Web Animations
  // AnimationEffectTimingReadOnly object.
  // https://drafts.csswg.org/date/2015-03-02/web-animations-css-integration/#web-animations-instantiation
  scoped_refptr<web_animations::AnimationEffectTimingReadOnly> timing_input(
      new web_animations::AnimationEffectTimingReadOnly(
          css_animation.delay(), base::TimeDelta(),
          CSSToWebFillMode(css_animation.fill_mode()), 0.0,
          css_animation.iteration_count(), css_animation.duration(),
          CSSToWebDirection(css_animation.direction()),
          cssom::TimingFunction::GetLinear()));

  // Construct the web_animations keyframe data from the CSS Animations keyframe
  // data.
  scoped_refptr<web_animations::KeyframeEffectReadOnly> keyframe_effect(
      new web_animations::KeyframeEffectReadOnly(
          timing_input, animatable_,
          ConvertCSSKeyframesToWebAnimationsKeyframes(
              *css_animation.keyframes(), css_animation.timing_function())));

  // Finally setup and play our animation.
  scoped_refptr<web_animations::Animation> web_animation(
      new web_animations::Animation(keyframe_effect,
                                    animatable_->GetDefaultTimeline()));

  // Setup an event handler on the animation so we can watch for when it enters
  // the after phase, allowing us to then trigger the animation events.
  scoped_ptr<web_animations::Animation::EventHandler> event_handler =
      web_animation->AttachEventHandler(
          base::Bind(&CSSAnimationsAdapter::HandleAnimationEnterAfterPhase,
                     base::Unretained(this), css_animation));

  // Track the animation in our map of all CSS Animations-created animations.
  DCHECK(animation_map_.find(css_animation.name()) == animation_map_.end());

  animation_map_.insert(std::make_pair(
      css_animation.name(),
      new AnimationWithEventHandler(web_animation, event_handler.Pass())));

  web_animation->Play();
}

void CSSAnimationsAdapter::OnAnimationRemoved(
    const cssom::Animation& css_animation) {
  // If a CSS Animation is removed from an element, its corresponding
  // Web Animations animation should be stopped and removed also.
  AnimationMap::iterator found = animation_map_.find(css_animation.name());
  DCHECK(animation_map_.end() != found);

  found->second->animation->Cancel();
  delete found->second;
  animation_map_.erase(found);
}

void CSSAnimationsAdapter::HandleAnimationEnterAfterPhase(
    const cssom::Animation& css_animation) {
  // https://drafts.csswg.org/date/2015-03-02/web-animations-css-integration/#css-animations-events
  animatable_->GetEventTarget()->DispatchEvent(new AnimationEvent(
      base::Tokens::animationend(), css_animation.name(),
      static_cast<float>(css_animation.duration().InMillisecondsF() *
                         css_animation.iteration_count())));
}

}  // namespace dom
}  // namespace cobalt
