17d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)// Copyright (c) 2013 The Chromium Authors. All rights reserved.
27d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
37d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)// found in the LICENSE file.
47d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
57d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "content/browser/web_contents/aura/window_slider.h"
67d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
7eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch#include <algorithm>
8eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
97d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "base/bind.h"
107d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "base/callback.h"
117d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "content/browser/web_contents/aura/shadow_layer_delegate.h"
127d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "content/public/browser/overscroll_configuration.h"
137d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "ui/aura/window.h"
147d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "ui/compositor/layer_animation_observer.h"
157d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "ui/compositor/scoped_layer_animation_settings.h"
16d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)#include "ui/events/event.h"
177d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
187d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)namespace content {
197d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
207d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)namespace {
217d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
227d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)// An animation observer that runs a callback at the end of the animation, and
237d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)// destroys itself.
247d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)class CallbackAnimationObserver : public ui::ImplicitAnimationObserver {
257d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) public:
267d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  CallbackAnimationObserver(const base::Closure& closure)
277d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      : closure_(closure) {
287d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  }
297d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
307d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  virtual ~CallbackAnimationObserver() {}
317d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
327d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) private:
337d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  // Overridden from ui::ImplicitAnimationObserver:
347d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  virtual void OnImplicitAnimationsCompleted() OVERRIDE {
357d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    if (!closure_.is_null())
367d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      closure_.Run();
377d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    base::MessageLoop::current()->DeleteSoon(FROM_HERE, this);
387d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  }
397d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
407d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  const base::Closure closure_;
417d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
427d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  DISALLOW_COPY_AND_ASSIGN(CallbackAnimationObserver);
437d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)};
447d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
457d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}  // namespace
467d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
477d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)WindowSlider::WindowSlider(Delegate* delegate,
487d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)                           aura::Window* event_window,
497d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)                           aura::Window* owner)
507d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    : delegate_(delegate),
517d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      event_window_(event_window),
527d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      owner_(owner),
53effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch      active_animator_(NULL),
547d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      delta_x_(0.f),
55424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)      active_start_threshold_(0.f),
56424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)      start_threshold_touchscreen_(content::GetOverscrollConfig(
57424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)          content::OVERSCROLL_CONFIG_HORIZ_THRESHOLD_START_TOUCHSCREEN)),
58424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)      start_threshold_touchpad_(content::GetOverscrollConfig(
59424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)          content::OVERSCROLL_CONFIG_HORIZ_THRESHOLD_START_TOUCHPAD)),
607d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      complete_threshold_(content::GetOverscrollConfig(
611320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci          content::OVERSCROLL_CONFIG_HORIZ_THRESHOLD_COMPLETE)),
621320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci      weak_factory_(this) {
637d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  event_window_->AddPreTargetHandler(this);
647d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
657d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  event_window_->AddObserver(this);
667d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  owner_->AddObserver(this);
677d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
687d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
697d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)WindowSlider::~WindowSlider() {
707d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (event_window_) {
717d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    event_window_->RemovePreTargetHandler(this);
727d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    event_window_->RemoveObserver(this);
737d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  }
747d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (owner_)
757d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    owner_->RemoveObserver(this);
76eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  delegate_->OnWindowSliderDestroyed();
777d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
787d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
797d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)void WindowSlider::ChangeOwner(aura::Window* new_owner) {
807d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (owner_)
817d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    owner_->RemoveObserver(this);
827d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  owner_ = new_owner;
837d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (owner_) {
847d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    owner_->AddObserver(this);
857d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    UpdateForScroll(0.f, 0.f);
867d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  }
877d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
887d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
89eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdochbool WindowSlider::IsSlideInProgress() const {
905d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  // if active_start_threshold_ is 0, it means that sliding hasn't been started
91effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  return active_start_threshold_ != 0 && (slider_.get() || active_animator_);
92eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch}
93eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
947d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)void WindowSlider::SetupSliderLayer() {
957d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  ui::Layer* parent = owner_->layer()->parent();
967d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  parent->Add(slider_.get());
977d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (delta_x_ < 0)
987d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    parent->StackAbove(slider_.get(), owner_->layer());
997d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  else
1007d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    parent->StackBelow(slider_.get(), owner_->layer());
1017d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  slider_->SetBounds(owner_->layer()->bounds());
1027d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  slider_->SetVisible(true);
1037d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
1047d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
1057d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)void WindowSlider::UpdateForScroll(float x_offset, float y_offset) {
106effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  if (active_animator_) {
107effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    // If there is an active animation, complete it before processing the scroll
108effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    // so that the callbacks that are invoked on the Delegate are consistent.
109effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    // Completing the animation may destroy WindowSlider through the animation
110effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    // callback, so we can't continue processing the scroll event here.
111effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    delta_x_ += x_offset;
112effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    CompleteActiveAnimations();
113effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    return;
114effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  }
115effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch
1167d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  float old_delta = delta_x_;
1177d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  delta_x_ += x_offset;
118424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)  if (fabs(delta_x_) < active_start_threshold_ && !slider_.get())
1197d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    return;
1207d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
1217d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if ((old_delta < 0 && delta_x_ > 0) ||
1227d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      (old_delta > 0 && delta_x_ < 0)) {
1237d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    slider_.reset();
1247d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    shadow_.reset();
1257d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  }
1267d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
1277d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  float translate = 0.f;
1287d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  ui::Layer* translate_layer = NULL;
1297d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
130eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  if (!slider_.get()) {
131eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch    slider_.reset(delta_x_ < 0 ? delegate_->CreateFrontLayer() :
132eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch                                 delegate_->CreateBackLayer());
133eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch    if (!slider_.get())
134eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch      return;
135eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch    SetupSliderLayer();
136eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  }
137eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
138424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)  if (delta_x_ <= -active_start_threshold_) {
139eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch    translate = owner_->bounds().width() +
140424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)        std::max(delta_x_ + active_start_threshold_,
141eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch                 static_cast<float>(-owner_->bounds().width()));
1427d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    translate_layer = slider_.get();
143424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)  } else if (delta_x_ >= active_start_threshold_) {
144424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)    translate = std::min(delta_x_ - active_start_threshold_,
145eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch                         static_cast<float>(owner_->bounds().width()));
1467d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    translate_layer = owner_->layer();
1477d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  } else {
148eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch    return;
1497d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  }
1507d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
1517d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (!shadow_.get())
1527d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    shadow_.reset(new ShadowLayerDelegate(translate_layer));
1537d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
1547d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  gfx::Transform transform;
1557d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  transform.Translate(translate, 0);
1567d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  translate_layer->SetTransform(transform);
1577d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
1587d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
159effb81e5f8246d0db0270817048dc992db66e9fbBen Murdochvoid WindowSlider::CompleteOrResetSlide() {
160eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  if (!slider_.get())
1617d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    return;
1627d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
1637d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  int width = owner_->bounds().width();
164424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)  float ratio = (fabs(delta_x_) - active_start_threshold_) / width;
1657d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (ratio < complete_threshold_) {
166effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    ResetSlide();
1677d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    return;
1687d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  }
1697d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
1707d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  ui::Layer* sliding = delta_x_ < 0 ? slider_.get() : owner_->layer();
171effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  active_animator_ = sliding->GetAnimator();
172effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch
173effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  ui::ScopedLayerAnimationSettings settings(active_animator_);
1747d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  settings.SetPreemptionStrategy(
1757d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET);
176d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)  settings.SetTweenType(gfx::Tween::EASE_OUT);
1777d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  settings.AddObserver(new CallbackAnimationObserver(
178effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch      base::Bind(&WindowSlider::SlideAnimationCompleted,
179effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch                 weak_factory_.GetWeakPtr(),
180effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch                 base::Passed(&slider_),
181effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch                 base::Passed(&shadow_))));
1827d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
1837d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  gfx::Transform transform;
1847d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  transform.Translate(delta_x_ < 0 ? 0 : width, 0);
185effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  delta_x_ = 0;
186effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  delegate_->OnWindowSlideCompleting();
1877d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  sliding->SetTransform(transform);
1887d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
1897d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
190effb81e5f8246d0db0270817048dc992db66e9fbBen Murdochvoid WindowSlider::CompleteActiveAnimations() {
191effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  if (active_animator_)
192effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    active_animator_->StopAnimating();
193effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch}
194effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch
195effb81e5f8246d0db0270817048dc992db66e9fbBen Murdochvoid WindowSlider::ResetSlide() {
1967d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (!slider_.get())
1977d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    return;
1987d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
1997d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  // Reset the state of the sliding layer.
2007d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (slider_.get()) {
201effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    ui::Layer* translate_layer;
2027d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    gfx::Transform transform;
203effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    if (delta_x_ < 0) {
204effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch      translate_layer = slider_.get();
205effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch      transform.Translate(translate_layer->bounds().width(), 0);
206effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    } else {
207effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch      translate_layer = owner_->layer();
208effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    }
209effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch
210effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    active_animator_ = translate_layer->GetAnimator();
211effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    ui::ScopedLayerAnimationSettings settings(active_animator_);
2127d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    settings.SetPreemptionStrategy(
2137d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)        ui::LayerAnimator::IMMEDIATELY_ANIMATE_TO_NEW_TARGET);
214d0247b1b59f9c528cb6df88b4f2b9afaf80d181eTorne (Richard Coles)    settings.SetTweenType(gfx::Tween::EASE_OUT);
2157d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    settings.AddObserver(new CallbackAnimationObserver(
216effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch        base::Bind(&WindowSlider::ResetSlideAnimationCompleted,
217effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch                   weak_factory_.GetWeakPtr(),
218effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch                   base::Passed(&slider_),
219effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch                   base::Passed(&shadow_))));
220effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    translate_layer->SetTransform(transform);
2217d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  }
2227d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
2237d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  delta_x_ = 0.f;
2247d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
2257d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
226effb81e5f8246d0db0270817048dc992db66e9fbBen Murdochvoid WindowSlider::SlideAnimationCompleted(
227effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    scoped_ptr<ui::Layer> layer, scoped_ptr<ShadowLayerDelegate> shadow) {
228effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  active_animator_ = NULL;
229effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  shadow.reset();
23046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  delegate_->OnWindowSlideCompleted(layer.Pass());
2317d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
2327d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
233effb81e5f8246d0db0270817048dc992db66e9fbBen Murdochvoid WindowSlider::ResetSlideAnimationCompleted(
234effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    scoped_ptr<ui::Layer> layer, scoped_ptr<ShadowLayerDelegate> shadow) {
235effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  active_animator_ = NULL;
236effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  shadow.reset();
237effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  layer.reset();
2387d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  delegate_->OnWindowSlideAborted();
2397d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
2407d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
2417d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)void WindowSlider::OnKeyEvent(ui::KeyEvent* event) {
242effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  ResetSlide();
2437d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
2447d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
2457d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)void WindowSlider::OnMouseEvent(ui::MouseEvent* event) {
2467d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (!(event->flags() & ui::EF_IS_SYNTHESIZED))
247effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    ResetSlide();
2487d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
2497d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
2507d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)void WindowSlider::OnScrollEvent(ui::ScrollEvent* event) {
251424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)  active_start_threshold_ = start_threshold_touchpad_;
2527d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (event->type() == ui::ET_SCROLL)
2537d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    UpdateForScroll(event->x_offset_ordinal(), event->y_offset_ordinal());
2547d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  else if (event->type() == ui::ET_SCROLL_FLING_START)
255effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    CompleteOrResetSlide();
2567d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  else
257effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch    ResetSlide();
2587d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  event->SetHandled();
2597d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
2607d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
2617d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)void WindowSlider::OnGestureEvent(ui::GestureEvent* event) {
262424c4d7b64af9d0d8fd9624f381f469654d5e3d2Torne (Richard Coles)  active_start_threshold_ = start_threshold_touchscreen_;
2637d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  const ui::GestureEventDetails& details = event->details();
2647d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  switch (event->type()) {
2657d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    case ui::ET_GESTURE_SCROLL_BEGIN:
266effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch      CompleteActiveAnimations();
2677d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      break;
2687d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
2697d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    case ui::ET_GESTURE_SCROLL_UPDATE:
2707d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      UpdateForScroll(details.scroll_x(), details.scroll_y());
2717d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      break;
2727d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
2737d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    case ui::ET_GESTURE_SCROLL_END:
274effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch      CompleteOrResetSlide();
2757d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      break;
2767d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
2777d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    case ui::ET_SCROLL_FLING_START:
278effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch      CompleteOrResetSlide();
2797d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      break;
2807d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
2817d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    case ui::ET_GESTURE_PINCH_BEGIN:
2827d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    case ui::ET_GESTURE_PINCH_UPDATE:
2837d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    case ui::ET_GESTURE_PINCH_END:
284effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch      ResetSlide();
2857d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      break;
2867d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
2877d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    default:
2887d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)      break;
2897d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  }
2907d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
2917d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  event->SetHandled();
2927d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
2937d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
294effb81e5f8246d0db0270817048dc992db66e9fbBen Murdochvoid WindowSlider::OnWindowRemovingFromRootWindow(aura::Window* window,
295effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch                                                  aura::Window* new_root) {
2967d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  if (window == event_window_) {
2977d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    window->RemoveObserver(this);
2987d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    window->RemovePreTargetHandler(this);
2997d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    event_window_ = NULL;
3007d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  } else if (window == owner_) {
3017d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    window->RemoveObserver(this);
3027d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    owner_ = NULL;
303eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch    delete this;
3047d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  } else {
3057d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)    NOTREACHED();
3067d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)  }
3077d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}
3087d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)
3097d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)}  // namespace content
310