15d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)// Copyright 2013 The Chromium Authors. All rights reserved.
290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)// found in the LICENSE file.
490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
55d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "content/renderer/input/input_handler_proxy.h"
690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
7e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch#include "base/auto_reset.h"
8116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "base/command_line.h"
990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include "base/debug/trace_event.h"
1090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#include "base/logging.h"
11eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch#include "base/metrics/histogram.h"
12e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch#include "content/common/input/did_overscroll_params.h"
1323730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)#include "content/common/input/web_input_event_traits.h"
14116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "content/public/common/content_switches.h"
155d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "content/renderer/input/input_handler_proxy_client.h"
16868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)#include "third_party/WebKit/public/platform/Platform.h"
177d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include "third_party/WebKit/public/web/WebInputEvent.h"
1868043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)#include "ui/events/latency_info.h"
19f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "ui/gfx/frame_time.h"
2023730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)#include "ui/gfx/geometry/point_conversions.h"
2190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
22f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)using blink::WebFloatPoint;
23f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)using blink::WebFloatSize;
24f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)using blink::WebGestureEvent;
25f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)using blink::WebInputEvent;
26f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)using blink::WebMouseEvent;
27f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)using blink::WebMouseWheelEvent;
28f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)using blink::WebPoint;
29f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)using blink::WebTouchEvent;
30a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)using blink::WebTouchPoint;
3190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
32eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdochnamespace {
33eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
345c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu// Maximum time between a fling event's timestamp and the first |Animate| call
355c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu// for the fling curve to use the fling timestamp as the initial animation time.
365c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu// Two frames allows a minor delay between event creation and the first animate.
375c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liuconst double kMaxSecondsFromFlingTimestampToFirstAnimate = 2. / 60.;
38f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
39a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch// Threshold for determining whether a fling scroll delta should have caused the
40a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch// client to scroll.
41a02191e04bc25c4935f804f2c080ae28663d096dBen Murdochconst float kScrollEpsilon = 0.1f;
42a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch
43010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)// Minimum fling velocity required for the active fling and new fling for the
44010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)// two to accumulate.
45010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)const double kMinBoostFlingSpeedSquare = 350. * 350.;
46010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
47010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)// Minimum velocity for the active touch scroll to preserve (boost) an active
48010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)// fling for which cancellation has been deferred.
49010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)const double kMinBoostTouchScrollSpeedSquare = 150 * 150.;
50010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
51010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)// Timeout window after which the active fling will be cancelled if no scrolls
52010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)// or flings of sufficient velocity relative to the current fling are received.
53010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)// The default value on Android native views is 40ms, but we use a slightly
54010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)// increased value to accomodate small IPC message delays.
55010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)const double kFlingBoostTimeoutDelaySeconds = 0.045;
56010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
57010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)gfx::Vector2dF ToClientScrollIncrement(const WebFloatSize& increment) {
58010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  return gfx::Vector2dF(-increment.width, -increment.height);
59010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)}
60010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
61f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)double InSecondsF(const base::TimeTicks& time) {
62f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  return (time - base::TimeTicks()).InSecondsF();
63f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)}
64f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
65010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)bool ShouldSuppressScrollForFlingBoosting(
66010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    const gfx::Vector2dF& current_fling_velocity,
67010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    const WebGestureEvent& scroll_update_event,
68010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    double time_since_last_boost_event) {
69010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  DCHECK_EQ(WebInputEvent::GestureScrollUpdate, scroll_update_event.type);
70010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
71010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  gfx::Vector2dF dx(scroll_update_event.data.scrollUpdate.deltaX,
72010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                    scroll_update_event.data.scrollUpdate.deltaY);
731320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  if (gfx::DotProduct(current_fling_velocity, dx) <= 0)
74010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return false;
75010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
76010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (time_since_last_boost_event < 0.001)
77010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return true;
78010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
79010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  // TODO(jdduke): Use |scroll_update_event.data.scrollUpdate.velocity{X,Y}|.
80010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  // The scroll must be of sufficient velocity to maintain the active fling.
81010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  const gfx::Vector2dF scroll_velocity =
82010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      gfx::ScaleVector2d(dx, 1. / time_since_last_boost_event);
83010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (scroll_velocity.LengthSquared() < kMinBoostTouchScrollSpeedSquare)
84010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return false;
85010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
86010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  return true;
87010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)}
88010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
89010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)bool ShouldBoostFling(const gfx::Vector2dF& current_fling_velocity,
90010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                      const WebGestureEvent& fling_start_event) {
91010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  DCHECK_EQ(WebInputEvent::GestureFlingStart, fling_start_event.type);
92010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
93010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  gfx::Vector2dF new_fling_velocity(
94010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      fling_start_event.data.flingStart.velocityX,
95010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      fling_start_event.data.flingStart.velocityY);
96010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
971320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  if (gfx::DotProduct(current_fling_velocity, new_fling_velocity) <= 0)
98010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return false;
99010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
100010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (current_fling_velocity.LengthSquared() < kMinBoostFlingSpeedSquare)
101010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return false;
102010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
103010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (new_fling_velocity.LengthSquared() < kMinBoostFlingSpeedSquare)
104010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return false;
105010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
106010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  return true;
107010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)}
108010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
109010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)WebGestureEvent ObtainGestureScrollBegin(const WebGestureEvent& event) {
110010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  WebGestureEvent scroll_begin_event = event;
111010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  scroll_begin_event.type = WebInputEvent::GestureScrollBegin;
112010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  scroll_begin_event.data.scrollBegin.deltaXHint = 0;
113010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  scroll_begin_event.data.scrollBegin.deltaYHint = 0;
114010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  return scroll_begin_event;
115010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)}
116010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
117eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdochvoid SendScrollLatencyUma(const WebInputEvent& event,
118eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch                          const ui::LatencyInfo& latency_info) {
119eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  if (!(event.type == WebInputEvent::GestureScrollBegin ||
120eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch        event.type == WebInputEvent::GestureScrollUpdate ||
121eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch        event.type == WebInputEvent::GestureScrollUpdateWithoutPropagation))
122eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch    return;
123eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
124eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  ui::LatencyInfo::LatencyMap::const_iterator it =
125eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch      latency_info.latency_components.find(std::make_pair(
126eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch          ui::INPUT_EVENT_LATENCY_ORIGINAL_COMPONENT, 0));
127eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
128eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  if (it == latency_info.latency_components.end())
129eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch    return;
130eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
131a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles)  base::TimeDelta delta = base::TimeTicks::HighResNow() - it->second.event_time;
132a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles)  for (size_t i = 0; i < it->second.event_count; ++i) {
133a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles)    UMA_HISTOGRAM_CUSTOM_COUNTS(
1345d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        "Event.Latency.RendererImpl.GestureScroll2",
135a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles)        delta.InMicroseconds(),
1365d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        1,
1375d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        1000000,
138a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles)        100);
139a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles)  }
140eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch}  // namespace
141eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
142eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch}
143eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
14490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)namespace content {
14590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
146010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)InputHandlerProxy::InputHandlerProxy(cc::InputHandler* input_handler,
147010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                                     InputHandlerProxyClient* client)
148010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    : client_(client),
14990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      input_handler_(input_handler),
150010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      deferred_fling_cancel_time_seconds_(0),
15190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#ifndef NDEBUG
15290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      expect_scroll_update_end_(false),
15390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#endif
15490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      gesture_scroll_on_impl_thread_(false),
15590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      gesture_pinch_on_impl_thread_(false),
156868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      fling_may_be_active_on_main_thread_(false),
1575d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      disallow_horizontal_fling_scroll_(false),
1585c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      disallow_vertical_fling_scroll_(false),
1595c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      has_fling_animation_started_(false) {
160010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  DCHECK(client);
16190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  input_handler_->BindToClient(this);
162116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch  smooth_scroll_enabled_ = CommandLine::ForCurrentProcess()->HasSwitch(
163116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch      switches::kEnableSmoothScrolling);
16490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
16590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
16690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)InputHandlerProxy::~InputHandlerProxy() {}
16790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
16890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)void InputHandlerProxy::WillShutdown() {
16990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  input_handler_ = NULL;
17090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  client_->WillShutdown();
17190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
17290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
173868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)InputHandlerProxy::EventDisposition
174868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)InputHandlerProxy::HandleInputEventWithLatencyInfo(
175868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    const WebInputEvent& event,
176a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)    ui::LatencyInfo* latency_info) {
17790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  DCHECK(input_handler_);
17890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
179a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  SendScrollLatencyUma(event, *latency_info);
180eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
1816e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)  TRACE_EVENT_FLOW_STEP0("input",
1826e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)                         "LatencyInfo.Flow",
1836e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)                         TRACE_ID_DONT_MANGLE(latency_info->trace_id),
1846e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)                         "HandleInputEventImpl");
185e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch
186a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  scoped_ptr<cc::SwapPromiseMonitor> latency_info_swap_promise_monitor =
187a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)      input_handler_->CreateLatencyInfoSwapPromiseMonitor(latency_info);
188868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  InputHandlerProxy::EventDisposition disposition = HandleInputEvent(event);
189868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  return disposition;
19090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
19190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
192868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)InputHandlerProxy::EventDisposition InputHandlerProxy::HandleInputEvent(
193868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    const WebInputEvent& event) {
194868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  DCHECK(input_handler_);
19523730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)  TRACE_EVENT1("input", "InputHandlerProxy::HandleInputEvent",
19623730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)               "type", WebInputEventTraits::GetName(event.type));
197868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)
1981320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  client_->DidReceiveInputEvent();
199010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (FilterInputEventForFlingBoosting(event))
200010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return DID_HANDLE;
201010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
20290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  if (event.type == WebInputEvent::MouseWheel) {
20390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    const WebMouseWheelEvent& wheel_event =
20490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        *static_cast<const WebMouseWheelEvent*>(&event);
20590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    if (wheel_event.scrollByPage) {
20690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      // TODO(jamesr): We don't properly handle scroll by page in the compositor
20790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      // thread, so punt it to the main thread. http://crbug.com/236639
208868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      return DID_NOT_HANDLE;
20990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    }
210a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)    if (wheel_event.modifiers & WebInputEvent::ControlKey) {
211a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)      // Wheel events involving the control key never trigger scrolling, only
212a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)      // event handlers.  Forward to the main thread.
213a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)      return DID_NOT_HANDLE;
214a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)    }
215116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch    if (smooth_scroll_enabled_) {
216116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch      cc::InputHandler::ScrollStatus scroll_status =
217116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch          input_handler_->ScrollAnimated(
218116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch              gfx::Point(wheel_event.x, wheel_event.y),
219116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch              gfx::Vector2dF(-wheel_event.deltaX, -wheel_event.deltaY));
220116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch      switch (scroll_status) {
221116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch        case cc::InputHandler::ScrollStarted:
222116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch          return DID_HANDLE;
223116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch        case cc::InputHandler::ScrollIgnored:
224116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch          return DROP_EVENT;
225116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch        default:
226116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch          return DID_NOT_HANDLE;
227116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch      }
228116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch    }
22990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    cc::InputHandler::ScrollStatus scroll_status = input_handler_->ScrollBegin(
23090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        gfx::Point(wheel_event.x, wheel_event.y), cc::InputHandler::Wheel);
23190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    switch (scroll_status) {
23290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      case cc::InputHandler::ScrollStarted: {
23390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        TRACE_EVENT_INSTANT2(
23423730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)            "input",
23590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)            "InputHandlerProxy::handle_input wheel scroll",
23690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)            TRACE_EVENT_SCOPE_THREAD,
23790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)            "deltaX",
23890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)            -wheel_event.deltaX,
23990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)            "deltaY",
24090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)            -wheel_event.deltaY);
24190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        bool did_scroll = input_handler_->ScrollBy(
24290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)            gfx::Point(wheel_event.x, wheel_event.y),
24390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)            gfx::Vector2dF(-wheel_event.deltaX, -wheel_event.deltaY));
24490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        input_handler_->ScrollEnd();
245868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)        return did_scroll ? DID_HANDLE : DROP_EVENT;
24690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      }
24790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      case cc::InputHandler::ScrollIgnored:
248868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)        // TODO(jamesr): This should be DROP_EVENT, but in cases where we fail
249868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)        // to properly sync scrollability it's safer to send the event to the
250868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)        // main thread. Change back to DROP_EVENT once we have synchronization
251868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)        // bugs sorted out.
252868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)        return DID_NOT_HANDLE;
2530529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch      case cc::InputHandler::ScrollUnknown:
25490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      case cc::InputHandler::ScrollOnMainThread:
255868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)        return DID_NOT_HANDLE;
2560529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch      case cc::InputHandler::ScrollStatusCount:
2570529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch        NOTREACHED();
2580529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch        break;
25990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    }
26090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else if (event.type == WebInputEvent::GestureScrollBegin) {
26190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    DCHECK(!gesture_scroll_on_impl_thread_);
26290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#ifndef NDEBUG
26390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    DCHECK(!expect_scroll_update_end_);
26490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    expect_scroll_update_end_ = true;
26590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#endif
26690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    const WebGestureEvent& gesture_event =
26790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        *static_cast<const WebGestureEvent*>(&event);
26890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    cc::InputHandler::ScrollStatus scroll_status = input_handler_->ScrollBegin(
26990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        gfx::Point(gesture_event.x, gesture_event.y),
27090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        cc::InputHandler::Gesture);
2710529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch    UMA_HISTOGRAM_ENUMERATION("Renderer4.CompositorScrollHitTestResult",
2720529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch                              scroll_status,
2730529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch                              cc::InputHandler::ScrollStatusCount);
27490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    switch (scroll_status) {
27590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      case cc::InputHandler::ScrollStarted:
276effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch        TRACE_EVENT_INSTANT0("input",
277effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch                             "InputHandlerProxy::handle_input gesture scroll",
278effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch                             TRACE_EVENT_SCOPE_THREAD);
27990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        gesture_scroll_on_impl_thread_ = true;
280868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)        return DID_HANDLE;
2810529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch      case cc::InputHandler::ScrollUnknown:
28290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      case cc::InputHandler::ScrollOnMainThread:
283868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)        return DID_NOT_HANDLE;
28490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      case cc::InputHandler::ScrollIgnored:
285868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)        return DROP_EVENT;
2860529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch      case cc::InputHandler::ScrollStatusCount:
2870529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch        NOTREACHED();
2880529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch        break;
28990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    }
29090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else if (event.type == WebInputEvent::GestureScrollUpdate) {
29190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#ifndef NDEBUG
29290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    DCHECK(expect_scroll_update_end_);
29390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#endif
29490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
29590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    if (!gesture_scroll_on_impl_thread_ && !gesture_pinch_on_impl_thread_)
296868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      return DID_NOT_HANDLE;
29790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
29890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    const WebGestureEvent& gesture_event =
29990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        *static_cast<const WebGestureEvent*>(&event);
30090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    bool did_scroll = input_handler_->ScrollBy(
30190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        gfx::Point(gesture_event.x, gesture_event.y),
30290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        gfx::Vector2dF(-gesture_event.data.scrollUpdate.deltaX,
30390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                       -gesture_event.data.scrollUpdate.deltaY));
304868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    return did_scroll ? DID_HANDLE : DROP_EVENT;
30590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else if (event.type == WebInputEvent::GestureScrollEnd) {
30690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#ifndef NDEBUG
30790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    DCHECK(expect_scroll_update_end_);
30890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    expect_scroll_update_end_ = false;
30990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#endif
310ba5b9a6411cb1792fd21f0a078d7a25cd1ceec16Ben Murdoch    input_handler_->ScrollEnd();
311ba5b9a6411cb1792fd21f0a078d7a25cd1ceec16Ben Murdoch
31290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    if (!gesture_scroll_on_impl_thread_)
313868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      return DID_NOT_HANDLE;
31490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
31590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    gesture_scroll_on_impl_thread_ = false;
316868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    return DID_HANDLE;
31790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else if (event.type == WebInputEvent::GesturePinchBegin) {
31890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    input_handler_->PinchGestureBegin();
3195d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    DCHECK(!gesture_pinch_on_impl_thread_);
32090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    gesture_pinch_on_impl_thread_ = true;
321868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    return DID_HANDLE;
32290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else if (event.type == WebInputEvent::GesturePinchEnd) {
3235d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    DCHECK(gesture_pinch_on_impl_thread_);
32490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    gesture_pinch_on_impl_thread_ = false;
32590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    input_handler_->PinchGestureEnd();
326868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    return DID_HANDLE;
32790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else if (event.type == WebInputEvent::GesturePinchUpdate) {
3285d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    DCHECK(gesture_pinch_on_impl_thread_);
32990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    const WebGestureEvent& gesture_event =
33090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        *static_cast<const WebGestureEvent*>(&event);
33190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    input_handler_->PinchGestureUpdate(
33290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        gesture_event.data.pinchUpdate.scale,
33390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        gfx::Point(gesture_event.x, gesture_event.y));
334868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    return DID_HANDLE;
33590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else if (event.type == WebInputEvent::GestureFlingStart) {
33690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    const WebGestureEvent& gesture_event =
33790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        *static_cast<const WebGestureEvent*>(&event);
33890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    return HandleGestureFling(gesture_event);
33990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else if (event.type == WebInputEvent::GestureFlingCancel) {
3406e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    if (CancelCurrentFling())
341868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      return DID_HANDLE;
34290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    else if (!fling_may_be_active_on_main_thread_)
343868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      return DROP_EVENT;
34490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else if (event.type == WebInputEvent::TouchStart) {
34590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    const WebTouchEvent& touch_event =
34690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        *static_cast<const WebTouchEvent*>(&event);
347a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)    for (size_t i = 0; i < touch_event.touchesLength; ++i) {
348a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)      if (touch_event.touches[i].state != WebTouchPoint::StatePressed)
349a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)        continue;
3505d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      if (input_handler_->HaveTouchEventHandlersAt(
35123730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)              gfx::Point(touch_event.touches[i].position.x,
35223730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)                         touch_event.touches[i].position.y))) {
353a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)        return DID_NOT_HANDLE;
3545d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      }
355a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)    }
356a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)    return DROP_EVENT;
35790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else if (WebInputEvent::isKeyboardEventType(event.type)) {
358a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch    // Only call |CancelCurrentFling()| if a fling was active, as it will
359a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch    // otherwise disrupt an in-progress touch scroll.
360a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch    if (fling_curve_)
3616e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      CancelCurrentFling();
36268043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)  } else if (event.type == WebInputEvent::MouseMove) {
36368043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)    const WebMouseEvent& mouse_event =
36468043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)        *static_cast<const WebMouseEvent*>(&event);
36568043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)    // TODO(tony): Ignore when mouse buttons are down?
3665d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    // TODO(davemoore): This should never happen, but bug #326635 showed some
3675d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    // surprising crashes.
3685d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    CHECK(input_handler_);
36968043e1e95eeb07d5cae7aca370b26518b0867d6Torne (Richard Coles)    input_handler_->MouseMoveAt(gfx::Point(mouse_event.x, mouse_event.y));
37090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  }
37190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
372868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  return DID_NOT_HANDLE;
37390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
37490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
37590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)InputHandlerProxy::EventDisposition
37690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)InputHandlerProxy::HandleGestureFling(
37790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    const WebGestureEvent& gesture_event) {
37890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  cc::InputHandler::ScrollStatus scroll_status;
37990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
38046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  if (gesture_event.sourceDevice == blink::WebGestureDeviceTouchpad) {
38190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    scroll_status = input_handler_->ScrollBegin(
38290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        gfx::Point(gesture_event.x, gesture_event.y),
38390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        cc::InputHandler::NonBubblingGesture);
38490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else {
38590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    if (!gesture_scroll_on_impl_thread_)
38690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      scroll_status = cc::InputHandler::ScrollOnMainThread;
38790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    else
38890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      scroll_status = input_handler_->FlingScrollBegin();
38990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  }
39090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
39190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#ifndef NDEBUG
39290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  expect_scroll_update_end_ = false;
39390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)#endif
39490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
39590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  switch (scroll_status) {
39690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    case cc::InputHandler::ScrollStarted: {
39746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)      if (gesture_event.sourceDevice == blink::WebGestureDeviceTouchpad)
39890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        input_handler_->ScrollEnd();
39990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
400010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      const float vx = gesture_event.data.flingStart.velocityX;
401010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      const float vy = gesture_event.data.flingStart.velocityY;
402010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      current_fling_velocity_ = gfx::Vector2dF(vx, vy);
40390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      fling_curve_.reset(client_->CreateFlingAnimationCurve(
40446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)          gesture_event.sourceDevice,
40546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)          WebFloatPoint(vx, vy),
40646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)          blink::WebSize()));
407010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      disallow_horizontal_fling_scroll_ = !vx;
408010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      disallow_vertical_fling_scroll_ = !vy;
409010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      TRACE_EVENT_ASYNC_BEGIN2("input",
410010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                               "InputHandlerProxy::HandleGestureFling::started",
411010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                               this,
412010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                               "vx",
413010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                               vx,
414010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                               "vy",
415010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                               vy);
4165c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      // Note that the timestamp will only be used to kickstart the animation if
4175c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      // its sufficiently close to the timestamp of the first call |Animate()|.
4185c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      has_fling_animation_started_ = false;
419010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      fling_parameters_.startTime = gesture_event.timeStampSeconds;
420010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      fling_parameters_.delta = WebFloatPoint(vx, vy);
42190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      fling_parameters_.point = WebPoint(gesture_event.x, gesture_event.y);
42290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      fling_parameters_.globalPoint =
42390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)          WebPoint(gesture_event.globalX, gesture_event.globalY);
42490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      fling_parameters_.modifiers = gesture_event.modifiers;
42590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      fling_parameters_.sourceDevice = gesture_event.sourceDevice;
4265c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      input_handler_->SetNeedsAnimate();
427868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      return DID_HANDLE;
42890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    }
4290529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch    case cc::InputHandler::ScrollUnknown:
43090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    case cc::InputHandler::ScrollOnMainThread: {
43123730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)      TRACE_EVENT_INSTANT0("input",
43290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                           "InputHandlerProxy::HandleGestureFling::"
43390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                           "scroll_on_main_thread",
43490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                           TRACE_EVENT_SCOPE_THREAD);
43590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      fling_may_be_active_on_main_thread_ = true;
436868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      return DID_NOT_HANDLE;
43790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    }
43890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    case cc::InputHandler::ScrollIgnored: {
43990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      TRACE_EVENT_INSTANT0(
44023730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)          "input",
44190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)          "InputHandlerProxy::HandleGestureFling::ignored",
44290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)          TRACE_EVENT_SCOPE_THREAD);
44346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)      if (gesture_event.sourceDevice == blink::WebGestureDeviceTouchpad) {
44490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        // We still pass the curve to the main thread if there's nothing
44590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        // scrollable, in case something
44690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        // registers a handler before the curve is over.
447868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)        return DID_NOT_HANDLE;
44890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      }
449868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      return DROP_EVENT;
45090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    }
4510529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch    case cc::InputHandler::ScrollStatusCount:
4520529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch      NOTREACHED();
4530529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch      break;
45490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  }
455868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  return DID_NOT_HANDLE;
45690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
45790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
458010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)bool InputHandlerProxy::FilterInputEventForFlingBoosting(
459010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    const WebInputEvent& event) {
460010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (!WebInputEvent::isGestureEventType(event.type))
461010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return false;
462010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
463010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (!fling_curve_) {
464010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    DCHECK(!deferred_fling_cancel_time_seconds_);
465010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return false;
466010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
467010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
468010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  const WebGestureEvent& gesture_event =
469010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      static_cast<const WebGestureEvent&>(event);
470010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (gesture_event.type == WebInputEvent::GestureFlingCancel) {
471010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    if (current_fling_velocity_.LengthSquared() < kMinBoostFlingSpeedSquare)
472010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      return false;
473010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
474010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    TRACE_EVENT_INSTANT0("input",
475010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                         "InputHandlerProxy::FlingBoostStart",
476010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                         TRACE_EVENT_SCOPE_THREAD);
477010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    deferred_fling_cancel_time_seconds_ =
478010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)        event.timeStampSeconds + kFlingBoostTimeoutDelaySeconds;
479010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return true;
480010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
481010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
482010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  // A fling is either inactive or is "free spinning", i.e., has yet to be
483010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  // interrupted by a touch gesture, in which case there is nothing to filter.
484010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (!deferred_fling_cancel_time_seconds_)
485010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return false;
486010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
487010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  // Gestures from a different source should immediately interrupt the fling.
488010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (gesture_event.sourceDevice != fling_parameters_.sourceDevice) {
4896e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    CancelCurrentFling();
490010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return false;
491010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
492010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
493010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  switch (gesture_event.type) {
494010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    case WebInputEvent::GestureTapCancel:
495010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    case WebInputEvent::GestureTapDown:
496010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      return false;
497010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
498010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    case WebInputEvent::GestureScrollBegin:
499010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      if (!input_handler_->IsCurrentlyScrollingLayerAt(
500010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)              gfx::Point(gesture_event.x, gesture_event.y),
50146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)              fling_parameters_.sourceDevice == blink::WebGestureDeviceTouchpad
502010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                  ? cc::InputHandler::NonBubblingGesture
503010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                  : cc::InputHandler::Gesture)) {
5046e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)        CancelCurrentFling();
505010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)        return false;
506010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      }
507010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
508010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      // TODO(jdduke): Use |gesture_event.data.scrollBegin.delta{X,Y}Hint| to
509010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      // determine if the ScrollBegin should immediately cancel the fling.
5106e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      ExtendBoostedFlingTimeout(gesture_event);
511010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      return true;
512010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
513010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    case WebInputEvent::GestureScrollUpdate: {
514010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      const double time_since_last_boost_event =
515010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)          event.timeStampSeconds - last_fling_boost_event_.timeStampSeconds;
516010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      if (ShouldSuppressScrollForFlingBoosting(current_fling_velocity_,
517010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                                               gesture_event,
518010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                                               time_since_last_boost_event)) {
5196e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)        ExtendBoostedFlingTimeout(gesture_event);
520010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)        return true;
521010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      }
522010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
5236e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      CancelCurrentFling();
524010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      return false;
525010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    }
526010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
527010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    case WebInputEvent::GestureScrollEnd:
5286e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      // Clear the last fling boost event *prior* to fling cancellation,
5296e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      // preventing insertion of a synthetic GestureScrollBegin.
5306e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      last_fling_boost_event_ = WebGestureEvent();
5316e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      CancelCurrentFling();
532010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      return true;
533010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
534010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    case WebInputEvent::GestureFlingStart: {
535010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      DCHECK_EQ(fling_parameters_.sourceDevice, gesture_event.sourceDevice);
536010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
537010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      bool fling_boosted =
538010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)          fling_parameters_.modifiers == gesture_event.modifiers &&
539010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)          ShouldBoostFling(current_fling_velocity_, gesture_event);
540010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
541010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      gfx::Vector2dF new_fling_velocity(
542010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)          gesture_event.data.flingStart.velocityX,
543010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)          gesture_event.data.flingStart.velocityY);
544010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
545010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      if (fling_boosted)
546010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)        current_fling_velocity_ += new_fling_velocity;
547010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      else
548010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)        current_fling_velocity_ = new_fling_velocity;
549010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
550010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      WebFloatPoint velocity(current_fling_velocity_.x(),
551010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                             current_fling_velocity_.y());
552010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      deferred_fling_cancel_time_seconds_ = 0;
5531320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci      disallow_horizontal_fling_scroll_ = !velocity.x;
5541320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci      disallow_vertical_fling_scroll_ = !velocity.y;
555010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      last_fling_boost_event_ = WebGestureEvent();
556010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      fling_curve_.reset(client_->CreateFlingAnimationCurve(
55746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)          gesture_event.sourceDevice,
55846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)          velocity,
55946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)          blink::WebSize()));
560010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      fling_parameters_.startTime = gesture_event.timeStampSeconds;
561010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      fling_parameters_.delta = velocity;
562010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      fling_parameters_.point = WebPoint(gesture_event.x, gesture_event.y);
563010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      fling_parameters_.globalPoint =
564010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)          WebPoint(gesture_event.globalX, gesture_event.globalY);
565010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
566010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      TRACE_EVENT_INSTANT2("input",
567010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                           fling_boosted ? "InputHandlerProxy::FlingBoosted"
568010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                                         : "InputHandlerProxy::FlingReplaced",
569010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                           TRACE_EVENT_SCOPE_THREAD,
570010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                           "vx",
571010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                           current_fling_velocity_.x(),
572010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                           "vy",
573010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)                           current_fling_velocity_.y());
574010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
575010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      // The client expects balanced calls between a consumed GestureFlingStart
576010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      // and |DidStopFlinging()|. TODO(jdduke): Provide a count parameter to
577010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      // |DidStopFlinging()| and only send after the accumulated fling ends.
578010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      client_->DidStopFlinging();
579010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      return true;
580010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    }
581010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
582010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    default:
583010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      // All other types of gestures (taps, presses, etc...) will complete the
584010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      // deferred fling cancellation.
5856e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      CancelCurrentFling();
586010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      return false;
587010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
588010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)}
589010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
5906e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)void InputHandlerProxy::ExtendBoostedFlingTimeout(
5916e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    const blink::WebGestureEvent& event) {
5926e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)  TRACE_EVENT_INSTANT0("input",
5936e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)                       "InputHandlerProxy::ExtendBoostedFlingTimeout",
5946e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)                       TRACE_EVENT_SCOPE_THREAD);
595010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  deferred_fling_cancel_time_seconds_ =
596010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      event.timeStampSeconds + kFlingBoostTimeoutDelaySeconds;
597010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  last_fling_boost_event_ = event;
598010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)}
599010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
60090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)void InputHandlerProxy::Animate(base::TimeTicks time) {
60190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  if (!fling_curve_)
60290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    return;
60390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
604f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  double monotonic_time_sec = InSecondsF(time);
605010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
606010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  if (deferred_fling_cancel_time_seconds_ &&
607010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      monotonic_time_sec > deferred_fling_cancel_time_seconds_) {
6086e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    CancelCurrentFling();
609010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    return;
610010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  }
611010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)
6125c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  if (!has_fling_animation_started_) {
6135c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    has_fling_animation_started_ = true;
6145c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    // Guard against invalid, future or sufficiently stale start times, as there
6155c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    // are no guarantees fling event and animation timestamps are compatible.
616010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    if (!fling_parameters_.startTime ||
6175c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu        monotonic_time_sec <= fling_parameters_.startTime ||
6185c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu        monotonic_time_sec >= fling_parameters_.startTime +
6195c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu                                  kMaxSecondsFromFlingTimestampToFirstAnimate) {
620010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      fling_parameters_.startTime = monotonic_time_sec;
621010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      input_handler_->SetNeedsAnimate();
622010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      return;
623010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)    }
6245c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  }
62590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
6265d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  bool fling_is_active =
6275d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      fling_curve_->apply(monotonic_time_sec - fling_parameters_.startTime,
6285d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)                          this);
6295d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
6305d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  if (disallow_vertical_fling_scroll_ && disallow_horizontal_fling_scroll_)
6315d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    fling_is_active = false;
6325d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
6335d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  if (fling_is_active) {
6345c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    input_handler_->SetNeedsAnimate();
63590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  } else {
63623730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)    TRACE_EVENT_INSTANT0("input",
63790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                         "InputHandlerProxy::animate::flingOver",
63890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                         TRACE_EVENT_SCOPE_THREAD);
6396e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    CancelCurrentFling();
64090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  }
64190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
64290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
64390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)void InputHandlerProxy::MainThreadHasStoppedFlinging() {
64490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  fling_may_be_active_on_main_thread_ = false;
6455d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  client_->DidStopFlinging();
64690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
64790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
648e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdochvoid InputHandlerProxy::DidOverscroll(
64903b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)    const gfx::PointF& causal_event_viewport_point,
650e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch    const gfx::Vector2dF& accumulated_overscroll,
651e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch    const gfx::Vector2dF& latest_overscroll_delta) {
65290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  DCHECK(client_);
653e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch
654a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch  TRACE_EVENT2("input",
655a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch               "InputHandlerProxy::DidOverscroll",
656a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch               "dx",
657a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch               latest_overscroll_delta.x(),
658a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch               "dy",
659a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch               latest_overscroll_delta.y());
660a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch
661e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch  DidOverscrollParams params;
662e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch  params.accumulated_overscroll = accumulated_overscroll;
663e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch  params.latest_overscroll_delta = latest_overscroll_delta;
664010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  params.current_fling_velocity =
665010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)      ToClientScrollIncrement(current_fling_velocity_);
66603b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)  params.causal_event_viewport_point = causal_event_viewport_point;
667e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch
668868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  if (fling_curve_) {
669868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    static const int kFlingOverscrollThreshold = 1;
6705d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    disallow_horizontal_fling_scroll_ |=
6719ab5563a3196760eb381d102cbb2bc0f7abc6a50Ben Murdoch        std::abs(params.accumulated_overscroll.x()) >=
6729ab5563a3196760eb381d102cbb2bc0f7abc6a50Ben Murdoch        kFlingOverscrollThreshold;
6735d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    disallow_vertical_fling_scroll_ |=
6749ab5563a3196760eb381d102cbb2bc0f7abc6a50Ben Murdoch        std::abs(params.accumulated_overscroll.y()) >=
6759ab5563a3196760eb381d102cbb2bc0f7abc6a50Ben Murdoch        kFlingOverscrollThreshold;
676868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  }
677868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)
6789ab5563a3196760eb381d102cbb2bc0f7abc6a50Ben Murdoch  client_->DidOverscroll(params);
67990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
68090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
6816e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)bool InputHandlerProxy::CancelCurrentFling() {
6826e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)  if (CancelCurrentFlingWithoutNotifyingClient()) {
6836e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    client_->DidStopFlinging();
6846e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    return true;
6856e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)  }
6866e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)  return false;
6876e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)}
6886e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)
6896e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)bool InputHandlerProxy::CancelCurrentFlingWithoutNotifyingClient() {
69090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  bool had_fling_animation = fling_curve_;
69190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  if (had_fling_animation &&
69246d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)      fling_parameters_.sourceDevice == blink::WebGestureDeviceTouchscreen) {
69390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    input_handler_->ScrollEnd();
69490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    TRACE_EVENT_ASYNC_END0(
69523730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)        "input",
69690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        "InputHandlerProxy::HandleGestureFling::started",
69790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)        this);
69890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  }
69990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
70023730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)  TRACE_EVENT_INSTANT1("input",
70190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                       "InputHandlerProxy::CancelCurrentFling",
70290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                       TRACE_EVENT_SCOPE_THREAD,
70390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                       "had_fling_animation",
70490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                       had_fling_animation);
70590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  fling_curve_.reset();
7065c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  has_fling_animation_started_ = false;
70790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  gesture_scroll_on_impl_thread_ = false;
708e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch  current_fling_velocity_ = gfx::Vector2dF();
709f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  fling_parameters_ = blink::WebActiveWheelFlingParameters();
7106e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)
7116e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)  if (deferred_fling_cancel_time_seconds_) {
7126e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    deferred_fling_cancel_time_seconds_ = 0;
7136e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)
7146e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    WebGestureEvent last_fling_boost_event = last_fling_boost_event_;
7156e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    last_fling_boost_event_ = WebGestureEvent();
7166e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    if (last_fling_boost_event.type == WebInputEvent::GestureScrollBegin ||
7176e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)        last_fling_boost_event.type == WebInputEvent::GestureScrollUpdate) {
7186e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      // Synthesize a GestureScrollBegin, as the original was suppressed.
7196e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      HandleInputEvent(ObtainGestureScrollBegin(last_fling_boost_event));
7206e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)    }
7216e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)  }
7226e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)
72390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  return had_fling_animation;
72490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
72590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
72690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)bool InputHandlerProxy::TouchpadFlingScroll(
72790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)    const WebFloatSize& increment) {
72890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  WebMouseWheelEvent synthetic_wheel;
72990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  synthetic_wheel.type = WebInputEvent::MouseWheel;
73090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  synthetic_wheel.deltaX = increment.width;
73190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  synthetic_wheel.deltaY = increment.height;
73290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  synthetic_wheel.hasPreciseScrollingDeltas = true;
73390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  synthetic_wheel.x = fling_parameters_.point.x;
73490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  synthetic_wheel.y = fling_parameters_.point.y;
73590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  synthetic_wheel.globalX = fling_parameters_.globalPoint.x;
73690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  synthetic_wheel.globalY = fling_parameters_.globalPoint.y;
73790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  synthetic_wheel.modifiers = fling_parameters_.modifiers;
73890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
73990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  InputHandlerProxy::EventDisposition disposition =
740868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      HandleInputEvent(synthetic_wheel);
74190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  switch (disposition) {
742868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    case DID_HANDLE:
74390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      return true;
744868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    case DROP_EVENT:
74590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      break;
746868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    case DID_NOT_HANDLE:
74723730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)      TRACE_EVENT_INSTANT0("input",
74890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                           "InputHandlerProxy::scrollBy::AbortFling",
74990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)                           TRACE_EVENT_SCOPE_THREAD);
750868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      // If we got a DID_NOT_HANDLE, that means we need to deliver wheels on the
75190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      // main thread. In this case we need to schedule a commit and transfer the
75290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      // fling curve over to the main thread and run the rest of the wheels from
75390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      // there. This can happen when flinging a page that contains a scrollable
75490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      // subarea that we can't scroll on the thread if the fling starts outside
75590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      // the subarea but then is flung "under" the pointer.
75690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      client_->TransferActiveWheelFlingAnimation(fling_parameters_);
75790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      fling_may_be_active_on_main_thread_ = true;
7586e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      CancelCurrentFlingWithoutNotifyingClient();
75990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      break;
76090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  }
76190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
76290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  return false;
76390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
76490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
765e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdochbool InputHandlerProxy::scrollBy(const WebFloatSize& increment,
766e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch                                 const WebFloatSize& velocity) {
767868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  WebFloatSize clipped_increment;
768e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch  WebFloatSize clipped_velocity;
769e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch  if (!disallow_horizontal_fling_scroll_) {
770868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    clipped_increment.width = increment.width;
771e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch    clipped_velocity.width = velocity.width;
772e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch  }
773e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch  if (!disallow_vertical_fling_scroll_) {
774868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    clipped_increment.height = increment.height;
775e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch    clipped_velocity.height = velocity.height;
776e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch  }
777868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)
778010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)  current_fling_velocity_ = clipped_velocity;
779a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch
780a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch  // Early out if the increment is zero, but avoid early terimination if the
781a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch  // velocity is still non-zero.
782868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)  if (clipped_increment == WebFloatSize())
783a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch    return clipped_velocity != WebFloatSize();
78490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
78523730a6e56a168d1879203e4b3819bb36e3d8f1fTorne (Richard Coles)  TRACE_EVENT2("input",
78690dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)               "InputHandlerProxy::scrollBy",
78790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)               "x",
788868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)               clipped_increment.width,
78990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)               "y",
790868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)               clipped_increment.height);
79190dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
79290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  bool did_scroll = false;
79390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
79490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  switch (fling_parameters_.sourceDevice) {
79546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    case blink::WebGestureDeviceTouchpad:
796868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      did_scroll = TouchpadFlingScroll(clipped_increment);
79790dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      break;
79846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    case blink::WebGestureDeviceTouchscreen:
799868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)      clipped_increment = ToClientScrollIncrement(clipped_increment);
80090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      did_scroll = input_handler_->ScrollBy(fling_parameters_.point,
801868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)                                            clipped_increment);
80290dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)      break;
80390dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  }
80490dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
80590dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  if (did_scroll) {
806868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    fling_parameters_.cumulativeScroll.width += clipped_increment.width;
807868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)    fling_parameters_.cumulativeScroll.height += clipped_increment.height;
80890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)  }
80990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
810a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch  // It's possible the provided |increment| is sufficiently small as to not
811a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch  // trigger a scroll, e.g., with a trivial time delta between fling updates.
812a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch  // Return true in this case to prevent early fling termination.
813a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch  if (std::abs(clipped_increment.width) < kScrollEpsilon &&
814a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch      std::abs(clipped_increment.height) < kScrollEpsilon)
815a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch    return true;
816a02191e04bc25c4935f804f2c080ae28663d096dBen Murdoch
817e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch  return did_scroll;
81890dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}
81990dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)
82090dce4d38c5ff5333bea97d859d4e484e27edf0cTorne (Richard Coles)}  // namespace content
821