gesture_provider_unittest.cc revision cedac228d2dd51db4b79ea1e72c7f249408ee061
1// Copyright 2014 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "base/basictypes.h"
6#include "base/logging.h"
7#include "base/memory/scoped_ptr.h"
8#include "base/message_loop/message_loop.h"
9#include "base/time/time.h"
10#include "testing/gtest/include/gtest/gtest.h"
11#include "ui/events/event_constants.h"
12#include "ui/events/gesture_detection/gesture_event_data.h"
13#include "ui/events/gesture_detection/gesture_provider.h"
14#include "ui/events/gesture_detection/mock_motion_event.h"
15#include "ui/events/gesture_detection/motion_event.h"
16#include "ui/gfx/geometry/point_f.h"
17
18using base::TimeDelta;
19using base::TimeTicks;
20
21namespace ui {
22namespace {
23
24const float kFakeCoordX = 42.f;
25const float kFakeCoordY = 24.f;
26const TimeDelta kOneSecond = TimeDelta::FromSeconds(1);
27const TimeDelta kOneMicrosecond = TimeDelta::FromMicroseconds(1);
28const TimeDelta kDeltaTimeForFlingSequences = TimeDelta::FromMilliseconds(5);
29const float kMockTouchRadius = MockMotionEvent::TOUCH_MAJOR / 2;
30const float kMaxTwoFingerTapSeparation = 300;
31
32GestureProvider::Config CreateDefaultConfig() {
33  GestureProvider::Config sConfig;
34  // The longpress timeout is non-zero only to indicate ordering with respect to
35  // the showpress timeout.
36  sConfig.gesture_detector_config.showpress_timeout = base::TimeDelta();
37  sConfig.gesture_detector_config.longpress_timeout = kOneMicrosecond;
38
39  // A valid doubletap timeout should always be non-zero. The value is used not
40  // only to trigger the timeout that confirms the tap event, but also to gate
41  // whether the second tap is in fact a double-tap (using a strict inequality
42  // between times for the first up and the second down events). We use 4
43  // microseconds simply to allow several intermediate events to occur before
44  // the second tap at microsecond intervals.
45  sConfig.gesture_detector_config.double_tap_timeout = kOneMicrosecond * 4;
46  return sConfig;
47}
48
49gfx::RectF BoundsForSingleMockTouchAtLocation(float x, float y) {
50  float diameter = MockMotionEvent::TOUCH_MAJOR;
51  return gfx::RectF(x - diameter / 2, y - diameter / 2, diameter, diameter);
52}
53
54}  // namespace
55
56class GestureProviderTest : public testing::Test, public GestureProviderClient {
57 public:
58  GestureProviderTest() {}
59  virtual ~GestureProviderTest() {}
60
61  static MockMotionEvent ObtainMotionEvent(base::TimeTicks event_time,
62                                           MotionEvent::Action action,
63                                           float x,
64                                           float y) {
65    return MockMotionEvent(action, event_time, x, y);
66  }
67
68  static MockMotionEvent ObtainMotionEvent(base::TimeTicks event_time,
69                                           MotionEvent::Action action,
70                                           float x0,
71                                           float y0,
72                                           float x1,
73                                           float y1) {
74    return MockMotionEvent(action, event_time, x0, y0, x1, y1);
75  }
76
77  static MockMotionEvent ObtainMotionEvent(
78      base::TimeTicks event_time,
79      MotionEvent::Action action,
80      const std::vector<gfx::PointF>& positions) {
81    switch (positions.size()) {
82      case 1:
83        return MockMotionEvent(
84            action, event_time, positions[0].x(), positions[0].y());
85      case 2:
86        return MockMotionEvent(action,
87                               event_time,
88                               positions[0].x(),
89                               positions[0].y(),
90                               positions[1].x(),
91                               positions[1].y());
92      case 3:
93        return MockMotionEvent(action,
94                               event_time,
95                               positions[0].x(),
96                               positions[0].y(),
97                               positions[1].x(),
98                               positions[1].y(),
99                               positions[2].x(),
100                               positions[2].y());
101      default:
102        CHECK(false) << "MockMotionEvent only supports 1-3 pointers";
103        return MockMotionEvent();
104    }
105  }
106
107  static MockMotionEvent ObtainMotionEvent(base::TimeTicks event_time,
108                                           MotionEvent::Action action) {
109    return ObtainMotionEvent(event_time, action, kFakeCoordX, kFakeCoordY);
110  }
111
112  // Test
113  virtual void SetUp() OVERRIDE { SetUpWithConfig(GetDefaultConfig()); }
114
115  virtual void TearDown() OVERRIDE {
116    gestures_.clear();
117    gesture_provider_.reset();
118  }
119
120  // GestureProviderClient
121  virtual void OnGestureEvent(const GestureEventData& gesture) OVERRIDE {
122    if (gesture.type == ET_GESTURE_SCROLL_BEGIN)
123      active_scroll_begin_event_.reset(new GestureEventData(gesture));
124    gestures_.push_back(gesture);
125  }
126
127  void SetUpWithConfig(const GestureProvider::Config& config) {
128    gesture_provider_.reset(new GestureProvider(config, this));
129    gesture_provider_->SetMultiTouchZoomSupportEnabled(false);
130  }
131
132  void ResetGestureDetection() {
133    CancelActiveTouchSequence();
134    gestures_.clear();
135  }
136  bool CancelActiveTouchSequence() {
137    if (!gesture_provider_->current_down_event())
138      return false;
139    return gesture_provider_->OnTouchEvent(
140        *gesture_provider_->current_down_event()->Cancel());
141  }
142
143  bool HasReceivedGesture(EventType type) const {
144    for (size_t i = 0; i < gestures_.size(); ++i) {
145      if (gestures_[i].type == type)
146        return true;
147    }
148    return false;
149  }
150
151  const GestureEventData& GetMostRecentGestureEvent() const {
152    EXPECT_FALSE(gestures_.empty());
153    return gestures_.back();
154  }
155
156  EventType GetMostRecentGestureEventType() const {
157    EXPECT_FALSE(gestures_.empty());
158    return gestures_.back().type;
159  }
160
161  size_t GetReceivedGestureCount() const { return gestures_.size(); }
162
163  const GestureEventData& GetReceivedGesture(size_t index) const {
164    EXPECT_LT(index, GetReceivedGestureCount());
165    return gestures_[index];
166  }
167
168  const GestureEventData* GetActiveScrollBeginEvent() const {
169    return active_scroll_begin_event_ ? active_scroll_begin_event_.get() : NULL;
170  }
171
172  const GestureProvider::Config& GetDefaultConfig() const {
173    static GestureProvider::Config sConfig = CreateDefaultConfig();
174    return sConfig;
175  }
176
177  float GetTouchSlop() const {
178    return GetDefaultConfig().gesture_detector_config.touch_slop;
179  }
180
181  float GetMinSwipeVelocity() const {
182    return GetDefaultConfig().gesture_detector_config.minimum_swipe_velocity;
183  }
184
185  base::TimeDelta GetLongPressTimeout() const {
186    return GetDefaultConfig().gesture_detector_config.longpress_timeout;
187  }
188
189  base::TimeDelta GetShowPressTimeout() const {
190    return GetDefaultConfig().gesture_detector_config.showpress_timeout;
191  }
192
193  base::TimeDelta GetDoubleTapTimeout() const {
194    return GetDefaultConfig().gesture_detector_config.double_tap_timeout;
195  }
196
197  void EnableBeginEndTypes() {
198    GestureProvider::Config config = GetDefaultConfig();
199    config.gesture_begin_end_types_enabled = true;
200    SetUpWithConfig(config);
201  }
202
203  void EnableSwipe() {
204    GestureProvider::Config config = GetDefaultConfig();
205    config.gesture_detector_config.swipe_enabled = true;
206    SetUpWithConfig(config);
207  }
208
209  void EnableTwoFingerTap(float max_distance_for_two_finger_tap,
210                          base::TimeDelta two_finger_tap_timeout) {
211    GestureProvider::Config config = GetDefaultConfig();
212    config.gesture_detector_config.two_finger_tap_enabled = true;
213    config.gesture_detector_config.two_finger_tap_max_separation =
214        max_distance_for_two_finger_tap;
215    config.gesture_detector_config.two_finger_tap_timeout =
216        two_finger_tap_timeout;
217    SetUpWithConfig(config);
218  }
219
220  void SetMinPinchUpdateSpanDelta(float min_pinch_update_span_delta) {
221    GestureProvider::Config config = GetDefaultConfig();
222    config.scale_gesture_detector_config.min_pinch_update_span_delta =
223        min_pinch_update_span_delta;
224    SetUpWithConfig(config);
225  }
226
227  bool HasDownEvent() const { return gesture_provider_->current_down_event(); }
228
229 protected:
230  void CheckScrollEventSequenceForEndActionType(
231      MotionEvent::Action end_action_type) {
232    base::TimeTicks event_time = base::TimeTicks::Now();
233    const float scroll_to_x = kFakeCoordX + 100;
234    const float scroll_to_y = kFakeCoordY + 100;
235    int motion_event_id = 0;
236
237    MockMotionEvent event =
238        ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
239    event.SetId(++motion_event_id);
240
241    EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
242
243    event = ObtainMotionEvent(event_time + kOneSecond,
244                              MotionEvent::ACTION_MOVE,
245                              scroll_to_x,
246                              scroll_to_y);
247    event.SetId(++motion_event_id);
248
249    EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
250    EXPECT_TRUE(gesture_provider_->IsScrollInProgress());
251    EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
252    EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
253    EXPECT_EQ(ET_GESTURE_SCROLL_UPDATE, GetMostRecentGestureEventType());
254    EXPECT_EQ(BoundsForSingleMockTouchAtLocation(scroll_to_x, scroll_to_y),
255              GetMostRecentGestureEvent().details.bounding_box());
256    ASSERT_EQ(3U, GetReceivedGestureCount()) << "Only TapDown, "
257                                                "ScrollBegin and ScrollBy "
258                                                "should have been sent";
259
260    EXPECT_EQ(ET_GESTURE_SCROLL_BEGIN, GetReceivedGesture(1).type);
261    EXPECT_EQ(motion_event_id, GetReceivedGesture(1).motion_event_id);
262    EXPECT_EQ(event_time + kOneSecond, GetReceivedGesture(1).time)
263        << "ScrollBegin should have the time of the ACTION_MOVE";
264
265    event = ObtainMotionEvent(
266        event_time + kOneSecond, end_action_type, scroll_to_x, scroll_to_y);
267    event.SetId(++motion_event_id);
268
269    gesture_provider_->OnTouchEvent(event);
270    EXPECT_FALSE(gesture_provider_->IsScrollInProgress());
271    EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_END));
272    EXPECT_EQ(ET_GESTURE_SCROLL_END, GetMostRecentGestureEventType());
273    EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
274    EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
275    EXPECT_EQ(BoundsForSingleMockTouchAtLocation(scroll_to_x, scroll_to_y),
276              GetMostRecentGestureEvent().details.bounding_box());
277  }
278
279  void OneFingerSwipe(float vx, float vy) {
280    std::vector<gfx::Vector2dF> velocities;
281    velocities.push_back(gfx::Vector2dF(vx, vy));
282    MultiFingerSwipe(velocities);
283  }
284
285  void TwoFingerSwipe(float vx0, float vy0, float vx1, float vy1) {
286    std::vector<gfx::Vector2dF> velocities;
287    velocities.push_back(gfx::Vector2dF(vx0, vy0));
288    velocities.push_back(gfx::Vector2dF(vx1, vy1));
289    MultiFingerSwipe(velocities);
290  }
291
292  void ThreeFingerSwipe(float vx0,
293                        float vy0,
294                        float vx1,
295                        float vy1,
296                        float vx2,
297                        float vy2) {
298    std::vector<gfx::Vector2dF> velocities;
299    velocities.push_back(gfx::Vector2dF(vx0, vy0));
300    velocities.push_back(gfx::Vector2dF(vx1, vy1));
301    velocities.push_back(gfx::Vector2dF(vx2, vy2));
302    MultiFingerSwipe(velocities);
303  }
304
305  void MultiFingerSwipe(std::vector<gfx::Vector2dF> velocities) {
306    ASSERT_GT(velocities.size(), 0U);
307
308    base::TimeTicks event_time = base::TimeTicks::Now();
309
310    std::vector<gfx::PointF> positions(velocities.size());
311    for (size_t i = 0; i < positions.size(); ++i)
312      positions[i] = gfx::PointF(kFakeCoordX * (i + 1), kFakeCoordY * (i + 1));
313
314    float dt = kDeltaTimeForFlingSequences.InSecondsF();
315
316    // Each pointer down should be a separate event.
317    for (size_t i = 0; i < positions.size(); ++i) {
318      const size_t pointer_count = i + 1;
319      std::vector<gfx::PointF> event_positions(pointer_count);
320      event_positions.assign(positions.begin(),
321                             positions.begin() + pointer_count);
322      MockMotionEvent event =
323          ObtainMotionEvent(event_time,
324                            pointer_count > 1 ? MotionEvent::ACTION_POINTER_DOWN
325                                              : MotionEvent::ACTION_DOWN,
326                            event_positions);
327      EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
328    }
329
330    for (size_t i = 0; i < positions.size(); ++i)
331      positions[i] += gfx::ScaleVector2d(velocities[i], dt);
332    MockMotionEvent event =
333        ObtainMotionEvent(event_time + kDeltaTimeForFlingSequences,
334                          MotionEvent::ACTION_MOVE,
335                          positions);
336    EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
337
338    for (size_t i = 0; i < positions.size(); ++i)
339      positions[i] += gfx::ScaleVector2d(velocities[i], dt);
340    event = ObtainMotionEvent(event_time + 2 * kDeltaTimeForFlingSequences,
341                              MotionEvent::ACTION_MOVE,
342                              positions);
343    EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
344
345    event = ObtainMotionEvent(event_time + 2 * kDeltaTimeForFlingSequences,
346                              MotionEvent::ACTION_POINTER_UP,
347                              positions);
348    EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
349  }
350
351  static void RunTasksAndWait(base::TimeDelta delay) {
352    base::MessageLoop::current()->PostDelayedTask(
353        FROM_HERE, base::MessageLoop::QuitClosure(), delay);
354    base::MessageLoop::current()->Run();
355  }
356
357  std::vector<GestureEventData> gestures_;
358  scoped_ptr<GestureProvider> gesture_provider_;
359  scoped_ptr<GestureEventData> active_scroll_begin_event_;
360  base::MessageLoopForUI message_loop_;
361};
362
363// Verify that a DOWN followed shortly by an UP will trigger a single tap.
364TEST_F(GestureProviderTest, GestureTapTap) {
365  base::TimeTicks event_time = base::TimeTicks::Now();
366  int motion_event_id = 0;
367
368  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(false);
369
370  MockMotionEvent event =
371      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
372  event.SetId(++motion_event_id);
373
374  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
375  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
376  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
377  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY),
378            GetMostRecentGestureEvent().details.bounding_box());
379
380  event = ObtainMotionEvent(event_time + kOneMicrosecond,
381                            MotionEvent::ACTION_UP);
382  event.SetId(++motion_event_id);
383
384  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
385  EXPECT_EQ(ET_GESTURE_TAP, GetMostRecentGestureEventType());
386  // Ensure tap details have been set.
387  EXPECT_EQ(1, GetMostRecentGestureEvent().details.tap_count());
388  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
389  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
390  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY),
391            GetMostRecentGestureEvent().details.bounding_box());
392}
393
394// Verify that a DOWN followed shortly by an UP will trigger
395// a ET_GESTURE_TAP_UNCONFIRMED event if double-tap is enabled.
396TEST_F(GestureProviderTest, GestureTapTapWithDelay) {
397  base::TimeTicks event_time = base::TimeTicks::Now();
398  int motion_event_id = 0;
399
400  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(true);
401
402  MockMotionEvent event =
403      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
404  event.SetId(++motion_event_id);
405
406  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
407  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
408  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
409  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
410  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY),
411            GetMostRecentGestureEvent().details.bounding_box());
412
413  event = ObtainMotionEvent(event_time + kOneMicrosecond,
414                            MotionEvent::ACTION_UP);
415  event.SetId(++motion_event_id);
416
417  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
418  EXPECT_EQ(ET_GESTURE_TAP_UNCONFIRMED, GetMostRecentGestureEventType());
419  // Ensure tap details have been set.
420  EXPECT_EQ(1, GetMostRecentGestureEvent().details.tap_count());
421  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
422  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
423  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY),
424            GetMostRecentGestureEvent().details.bounding_box());
425
426  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_TAP));
427  RunTasksAndWait(GetDoubleTapTimeout());
428  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_TAP));
429}
430
431// Verify that a DOWN followed by a MOVE will trigger fling (but not LONG).
432TEST_F(GestureProviderTest, GestureFlingAndCancelLongPress) {
433  base::TimeTicks event_time = TimeTicks::Now();
434  base::TimeDelta delta_time = kDeltaTimeForFlingSequences;
435  int motion_event_id = 0;
436
437  MockMotionEvent event =
438      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
439  event.SetId(++motion_event_id);
440
441  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
442  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
443  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
444  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
445
446  event = ObtainMotionEvent(event_time + delta_time,
447                            MotionEvent::ACTION_MOVE,
448                            kFakeCoordX * 10,
449                            kFakeCoordY * 10);
450  event.SetId(++motion_event_id);
451  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
452
453  event = ObtainMotionEvent(event_time + delta_time * 2,
454                            MotionEvent::ACTION_UP,
455                            kFakeCoordX * 10,
456                            kFakeCoordY * 10);
457  event.SetId(++motion_event_id);
458
459  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
460  EXPECT_EQ(ET_SCROLL_FLING_START, GetMostRecentGestureEventType());
461  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
462  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
463  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_LONG_PRESS));
464  EXPECT_EQ(
465      BoundsForSingleMockTouchAtLocation(kFakeCoordX * 10, kFakeCoordY * 10),
466      GetMostRecentGestureEvent().details.bounding_box());
467}
468
469// Verify that for a normal scroll the following events are sent:
470// - ET_GESTURE_SCROLL_BEGIN
471// - ET_GESTURE_SCROLL_UPDATE
472// - ET_GESTURE_SCROLL_END
473TEST_F(GestureProviderTest, ScrollEventActionUpSequence) {
474  CheckScrollEventSequenceForEndActionType(MotionEvent::ACTION_UP);
475}
476
477// Verify that for a cancelled scroll the following events are sent:
478// - ET_GESTURE_SCROLL_BEGIN
479// - ET_GESTURE_SCROLL_UPDATE
480// - ET_GESTURE_SCROLL_END
481TEST_F(GestureProviderTest, ScrollEventActionCancelSequence) {
482  CheckScrollEventSequenceForEndActionType(MotionEvent::ACTION_CANCEL);
483}
484
485// Verify that for a normal fling (fling after scroll) the following events are
486// sent:
487// - ET_GESTURE_SCROLL_BEGIN
488// - ET_SCROLL_FLING_START
489TEST_F(GestureProviderTest, FlingEventSequence) {
490  base::TimeTicks event_time = base::TimeTicks::Now();
491  base::TimeDelta delta_time = kDeltaTimeForFlingSequences;
492  int motion_event_id = 0;
493
494  MockMotionEvent event =
495      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
496  event.SetId(++motion_event_id);
497
498  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
499
500  event = ObtainMotionEvent(event_time + delta_time,
501                            MotionEvent::ACTION_MOVE,
502                            kFakeCoordX * 5,
503                            kFakeCoordY * 5);
504  event.SetId(++motion_event_id);
505
506  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
507  EXPECT_TRUE(gesture_provider_->IsScrollInProgress());
508  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
509  EXPECT_EQ(ET_GESTURE_SCROLL_UPDATE, GetMostRecentGestureEventType());
510  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
511  ASSERT_EQ(3U, GetReceivedGestureCount());
512  ASSERT_EQ(ET_GESTURE_SCROLL_BEGIN, GetReceivedGesture(1).type);
513  EXPECT_EQ(motion_event_id, GetReceivedGesture(1).motion_event_id);
514
515  // We don't want to take a dependency here on exactly how hints are calculated
516  // for a fling (eg. may depend on velocity), so just validate the direction.
517  int hint_x = GetReceivedGesture(1).details.scroll_x_hint();
518  int hint_y = GetReceivedGesture(1).details.scroll_y_hint();
519  EXPECT_TRUE(hint_x > 0 && hint_y > 0 && hint_x > hint_y)
520      << "ScrollBegin hint should be in positive X axis";
521
522  event = ObtainMotionEvent(event_time + delta_time * 2,
523                            MotionEvent::ACTION_UP,
524                            kFakeCoordX * 10,
525                            kFakeCoordY * 10);
526  event.SetId(++motion_event_id);
527
528  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
529  EXPECT_FALSE(gesture_provider_->IsScrollInProgress());
530  EXPECT_EQ(ET_SCROLL_FLING_START, GetMostRecentGestureEventType());
531  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
532  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
533  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_SCROLL_END));
534  EXPECT_EQ(event_time + delta_time * 2, GetMostRecentGestureEvent().time)
535      << "FlingStart should have the time of the ACTION_UP";
536}
537
538TEST_F(GestureProviderTest, GestureCancelledWhenWindowFocusLost) {
539  const base::TimeTicks event_time = TimeTicks::Now();
540
541  MockMotionEvent event =
542      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
543  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
544  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
545
546  RunTasksAndWait(GetLongPressTimeout() + GetShowPressTimeout() +
547                  kOneMicrosecond);
548  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SHOW_PRESS));
549  EXPECT_EQ(ET_GESTURE_LONG_PRESS, GetMostRecentGestureEventType());
550
551  // The long press triggers window focus loss by opening a context menu.
552  EXPECT_TRUE(CancelActiveTouchSequence());
553  EXPECT_FALSE(HasDownEvent());
554
555  // A final ACTION_UP should have no effect.
556  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
557                            MotionEvent::ACTION_UP);
558  EXPECT_FALSE(gesture_provider_->OnTouchEvent(event));
559}
560
561TEST_F(GestureProviderTest, NoTapAfterScrollBegins) {
562  base::TimeTicks event_time = base::TimeTicks::Now();
563
564  MockMotionEvent event =
565      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
566
567  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
568
569  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
570  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
571  event = ObtainMotionEvent(event_time + kOneMicrosecond,
572                            MotionEvent::ACTION_MOVE,
573                            kFakeCoordX + 50,
574                            kFakeCoordY + 50);
575  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
576  EXPECT_EQ(ET_GESTURE_SCROLL_UPDATE, GetMostRecentGestureEventType());
577
578  event = ObtainMotionEvent(event_time + kOneSecond,
579                            MotionEvent::ACTION_UP,
580                            kFakeCoordX + 50,
581                            kFakeCoordY + 50);
582  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
583  EXPECT_EQ(ET_GESTURE_SCROLL_END, GetMostRecentGestureEventType());
584  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_LONG_TAP));
585}
586
587TEST_F(GestureProviderTest, DoubleTap) {
588  base::TimeTicks event_time = base::TimeTicks::Now();
589
590  MockMotionEvent event =
591      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
592  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
593
594  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
595  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
596
597  event = ObtainMotionEvent(event_time + kOneMicrosecond,
598                            MotionEvent::ACTION_UP,
599                            kFakeCoordX,
600                            kFakeCoordY);
601  gesture_provider_->OnTouchEvent(event);
602  EXPECT_EQ(ET_GESTURE_TAP_UNCONFIRMED, GetMostRecentGestureEventType());
603  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
604
605  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
606                            MotionEvent::ACTION_DOWN,
607                            kFakeCoordX,
608                            kFakeCoordY);
609  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
610  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
611  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
612
613  // Moving a very small amount of distance should not trigger the double tap
614  // drag zoom mode.
615  event = ObtainMotionEvent(event_time + kOneMicrosecond * 3,
616                            MotionEvent::ACTION_MOVE,
617                            kFakeCoordX,
618                            kFakeCoordY + 1);
619  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
620  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
621  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
622
623  event = ObtainMotionEvent(event_time + kOneMicrosecond * 3,
624                            MotionEvent::ACTION_UP,
625                            kFakeCoordX,
626                            kFakeCoordY + 1);
627  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
628
629  const GestureEventData& double_tap = GetMostRecentGestureEvent();
630  EXPECT_EQ(ET_GESTURE_DOUBLE_TAP, double_tap.type);
631  // Ensure tap details have been set.
632  EXPECT_EQ(10, double_tap.details.bounding_box().width());
633  EXPECT_EQ(10, double_tap.details.bounding_box().height());
634  EXPECT_EQ(1, double_tap.details.tap_count());
635}
636
637TEST_F(GestureProviderTest, DoubleTapDragZoomBasic) {
638  const base::TimeTicks down_time_1 = TimeTicks::Now();
639  const base::TimeTicks down_time_2 = down_time_1 + kOneMicrosecond * 2;
640
641  MockMotionEvent event =
642      ObtainMotionEvent(down_time_1, MotionEvent::ACTION_DOWN);
643  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
644
645  event = ObtainMotionEvent(down_time_1 + kOneMicrosecond,
646                            MotionEvent::ACTION_UP,
647                            kFakeCoordX,
648                            kFakeCoordY);
649  gesture_provider_->OnTouchEvent(event);
650  EXPECT_EQ(ET_GESTURE_TAP_UNCONFIRMED, GetMostRecentGestureEventType());
651  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
652
653  event = ObtainMotionEvent(
654      down_time_2, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
655  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
656  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
657  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
658
659  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond,
660                            MotionEvent::ACTION_MOVE,
661                            kFakeCoordX,
662                            kFakeCoordY + 100);
663  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
664  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
665  ASSERT_EQ(ET_GESTURE_PINCH_BEGIN, GetMostRecentGestureEventType());
666  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY + 100),
667            GetMostRecentGestureEvent().details.bounding_box());
668
669  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 2,
670                            MotionEvent::ACTION_MOVE,
671                            kFakeCoordX,
672                            kFakeCoordY + 200);
673  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
674  ASSERT_EQ(ET_GESTURE_PINCH_UPDATE, GetMostRecentGestureEventType());
675  EXPECT_LT(1.f, GetMostRecentGestureEvent().details.scale());
676  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY + 200),
677            GetMostRecentGestureEvent().details.bounding_box());
678
679  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 3,
680                            MotionEvent::ACTION_MOVE,
681                            kFakeCoordX,
682                            kFakeCoordY + 100);
683  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
684  ASSERT_EQ(ET_GESTURE_PINCH_UPDATE, GetMostRecentGestureEventType());
685  EXPECT_GT(1.f, GetMostRecentGestureEvent().details.scale());
686  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY + 100),
687            GetMostRecentGestureEvent().details.bounding_box());
688
689  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 4,
690                            MotionEvent::ACTION_UP,
691                            kFakeCoordX,
692                            kFakeCoordY - 200);
693  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
694  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_PINCH_END));
695  EXPECT_EQ(ET_GESTURE_SCROLL_END, GetMostRecentGestureEventType());
696  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY - 200),
697            GetMostRecentGestureEvent().details.bounding_box());
698}
699
700// Generate a scroll gesture and verify that the resulting scroll motion event
701// has both absolute and relative position information.
702TEST_F(GestureProviderTest, ScrollUpdateValues) {
703  const float delta_x = 16;
704  const float delta_y = 84;
705
706  const base::TimeTicks event_time = TimeTicks::Now();
707
708  MockMotionEvent event =
709      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
710  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
711
712  // Move twice so that we get two ET_GESTURE_SCROLL_UPDATE events and can
713  // compare the relative and absolute coordinates.
714  event = ObtainMotionEvent(event_time + kOneMicrosecond,
715                            MotionEvent::ACTION_MOVE,
716                            kFakeCoordX - delta_x / 2,
717                            kFakeCoordY - delta_y / 2);
718  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
719
720  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
721                            MotionEvent::ACTION_MOVE,
722                            kFakeCoordX - delta_x,
723                            kFakeCoordY - delta_y);
724  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
725
726  // Make sure the reported gesture event has all the expected details.
727  ASSERT_LT(0U, GetReceivedGestureCount());
728  GestureEventData gesture = GetMostRecentGestureEvent();
729  EXPECT_EQ(ET_GESTURE_SCROLL_UPDATE, gesture.type);
730  EXPECT_EQ(event_time + kOneMicrosecond * 2, gesture.time);
731  EXPECT_EQ(kFakeCoordX - delta_x, gesture.x);
732  EXPECT_EQ(kFakeCoordY - delta_y, gesture.y);
733  EXPECT_EQ(1, gesture.details.touch_points());
734
735  // No horizontal delta because of snapping.
736  EXPECT_EQ(0, gesture.details.scroll_x());
737  EXPECT_EQ(-delta_y / 2, gesture.details.scroll_y());
738}
739
740// Verify that fractional scroll deltas are rounded as expected and that
741// fractional scrolling doesn't break scroll snapping.
742TEST_F(GestureProviderTest, FractionalScroll) {
743  const float delta_x = 0.4f;
744  const float delta_y = 5.2f;
745
746  const base::TimeTicks event_time = TimeTicks::Now();
747
748  MockMotionEvent event =
749      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
750  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
751
752  // Skip past the touch slop and move back.
753  event = ObtainMotionEvent(event_time,
754                            MotionEvent::ACTION_MOVE,
755                            kFakeCoordX,
756                            kFakeCoordY + 100);
757  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
758  event = ObtainMotionEvent(event_time,
759                            MotionEvent::ACTION_MOVE);
760  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
761
762  // Now move up slowly, mostly vertically but with a (fractional) bit of
763  // horizontal motion.
764  for(int i = 1; i <= 10; i++) {
765    event = ObtainMotionEvent(event_time + kOneMicrosecond * i,
766                              MotionEvent::ACTION_MOVE,
767                              kFakeCoordX + delta_x * i,
768                              kFakeCoordY + delta_y * i);
769    EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
770
771    ASSERT_LT(0U, GetReceivedGestureCount());
772    GestureEventData gesture = GetMostRecentGestureEvent();
773    EXPECT_EQ(ET_GESTURE_SCROLL_UPDATE, gesture.type);
774    EXPECT_EQ(event_time + kOneMicrosecond * i, gesture.time);
775    EXPECT_EQ(1, gesture.details.touch_points());
776
777    // Verify that the event co-ordinates are still the precise values we
778    // supplied.
779    EXPECT_EQ(kFakeCoordX + delta_x * i, gesture.x);
780    EXPECT_EQ(kFakeCoordY + delta_y * i, gesture.y);
781
782    // Verify that we're scrolling vertically by the expected amount
783    // (modulo rounding).
784    EXPECT_GE(gesture.details.scroll_y(), (int)delta_y);
785    EXPECT_LE(gesture.details.scroll_y(), ((int)delta_y) + 1);
786
787    // And that there has been no horizontal motion at all.
788    EXPECT_EQ(0, gesture.details.scroll_x());
789  }
790}
791
792// Generate a scroll gesture and verify that the resulting scroll begin event
793// has the expected hint values.
794TEST_F(GestureProviderTest, ScrollBeginValues) {
795  const float delta_x = 13;
796  const float delta_y = 89;
797
798  const base::TimeTicks event_time = TimeTicks::Now();
799
800  MockMotionEvent event =
801      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
802  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
803
804  // Move twice such that the first event isn't sufficient to start
805  // scrolling on it's own.
806  event = ObtainMotionEvent(event_time + kOneMicrosecond,
807                            MotionEvent::ACTION_MOVE,
808                            kFakeCoordX + 2,
809                            kFakeCoordY + 1);
810  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
811  EXPECT_FALSE(gesture_provider_->IsScrollInProgress());
812
813  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
814                            MotionEvent::ACTION_MOVE,
815                            kFakeCoordX + delta_x,
816                            kFakeCoordY + delta_y);
817  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
818  EXPECT_TRUE(gesture_provider_->IsScrollInProgress());
819
820  const GestureEventData* scroll_begin_gesture = GetActiveScrollBeginEvent();
821  ASSERT_TRUE(!!scroll_begin_gesture);
822  EXPECT_EQ(delta_x, scroll_begin_gesture->details.scroll_x_hint());
823  EXPECT_EQ(delta_y, scroll_begin_gesture->details.scroll_y_hint());
824}
825
826TEST_F(GestureProviderTest, LongPressAndTapCancelledWhenScrollBegins) {
827  base::TimeTicks event_time = base::TimeTicks::Now();
828
829  MockMotionEvent event =
830      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
831  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
832  event = ObtainMotionEvent(event_time + kOneMicrosecond,
833                            MotionEvent::ACTION_MOVE,
834                            kFakeCoordX * 5,
835                            kFakeCoordY * 5);
836  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
837  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
838                            MotionEvent::ACTION_MOVE,
839                            kFakeCoordX * 10,
840                            kFakeCoordY * 10);
841  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
842
843  const base::TimeDelta long_press_timeout =
844      GetLongPressTimeout() + GetShowPressTimeout() + kOneMicrosecond;
845  RunTasksAndWait(long_press_timeout);
846
847  // No LONG_TAP as the LONG_PRESS timer is cancelled.
848  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_LONG_PRESS));
849  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_LONG_TAP));
850}
851
852// Verify that LONG_TAP is triggered after LONG_PRESS followed by an UP.
853TEST_F(GestureProviderTest, GestureLongTap) {
854  base::TimeTicks event_time = base::TimeTicks::Now();
855
856  MockMotionEvent event =
857      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
858  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
859
860  const base::TimeDelta long_press_timeout =
861      GetLongPressTimeout() + GetShowPressTimeout() + kOneMicrosecond;
862  RunTasksAndWait(long_press_timeout);
863
864  EXPECT_EQ(ET_GESTURE_LONG_PRESS, GetMostRecentGestureEventType());
865  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
866  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY),
867            GetMostRecentGestureEvent().details.bounding_box());
868
869  event = ObtainMotionEvent(event_time + kOneSecond, MotionEvent::ACTION_UP);
870  gesture_provider_->OnTouchEvent(event);
871  EXPECT_EQ(ET_GESTURE_LONG_TAP, GetMostRecentGestureEventType());
872  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
873  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY),
874            GetMostRecentGestureEvent().details.bounding_box());
875}
876
877TEST_F(GestureProviderTest, GestureLongPressDoesNotPreventScrolling) {
878  base::TimeTicks event_time = base::TimeTicks::Now();
879
880  MockMotionEvent event =
881      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
882  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
883
884  const base::TimeDelta long_press_timeout =
885      GetLongPressTimeout() + GetShowPressTimeout() + kOneMicrosecond;
886  RunTasksAndWait(long_press_timeout);
887
888  EXPECT_EQ(ET_GESTURE_LONG_PRESS, GetMostRecentGestureEventType());
889  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
890  event = ObtainMotionEvent(event_time + long_press_timeout,
891                            MotionEvent::ACTION_MOVE,
892                            kFakeCoordX + 100,
893                            kFakeCoordY + 100);
894  gesture_provider_->OnTouchEvent(event);
895
896  EXPECT_EQ(ET_GESTURE_SCROLL_UPDATE, GetMostRecentGestureEventType());
897  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
898  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
899
900  event = ObtainMotionEvent(event_time + long_press_timeout,
901                            MotionEvent::ACTION_UP);
902  gesture_provider_->OnTouchEvent(event);
903  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_LONG_TAP));
904}
905
906TEST_F(GestureProviderTest, NoGestureLongPressDuringDoubleTap) {
907  base::TimeTicks event_time = base::TimeTicks::Now();
908  int motion_event_id = 0;
909
910  MockMotionEvent event = ObtainMotionEvent(
911      event_time, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
912  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
913
914  event = ObtainMotionEvent(event_time + kOneMicrosecond,
915                            MotionEvent::ACTION_UP,
916                            kFakeCoordX,
917                            kFakeCoordY);
918  gesture_provider_->OnTouchEvent(event);
919  EXPECT_EQ(ET_GESTURE_TAP_UNCONFIRMED, GetMostRecentGestureEventType());
920  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
921
922  event = ObtainMotionEvent(event_time + kOneMicrosecond,
923                            MotionEvent::ACTION_DOWN,
924                            kFakeCoordX,
925                            kFakeCoordY);
926  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
927  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
928  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
929  EXPECT_TRUE(gesture_provider_->IsDoubleTapInProgress());
930
931  const base::TimeDelta long_press_timeout =
932      GetLongPressTimeout() + GetShowPressTimeout() + kOneMicrosecond;
933  RunTasksAndWait(long_press_timeout);
934  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_LONG_PRESS));
935
936  event = ObtainMotionEvent(event_time + long_press_timeout,
937                            MotionEvent::ACTION_MOVE,
938                            kFakeCoordX + 20,
939                            kFakeCoordY + 20);
940  event.SetId(++motion_event_id);
941
942  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
943  EXPECT_EQ(ET_GESTURE_PINCH_BEGIN, GetMostRecentGestureEventType());
944  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
945  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
946  EXPECT_TRUE(gesture_provider_->IsDoubleTapInProgress());
947
948  event = ObtainMotionEvent(event_time + long_press_timeout + kOneMicrosecond,
949                            MotionEvent::ACTION_UP,
950                            kFakeCoordX,
951                            kFakeCoordY + 1);
952  event.SetId(++motion_event_id);
953  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
954  EXPECT_EQ(ET_GESTURE_SCROLL_END, GetMostRecentGestureEventType());
955  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
956  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
957  EXPECT_FALSE(gesture_provider_->IsDoubleTapInProgress());
958}
959
960// Verify that the touch slop region is removed from the first scroll delta to
961// avoid a jump when starting to scroll.
962TEST_F(GestureProviderTest, TouchSlopRemovedFromScroll) {
963  const float touch_slop = GetTouchSlop();
964  const float scroll_delta = 5;
965
966  base::TimeTicks event_time = base::TimeTicks::Now();
967
968  MockMotionEvent event =
969      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
970  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
971
972  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
973                            MotionEvent::ACTION_MOVE,
974                            kFakeCoordX,
975                            kFakeCoordY + touch_slop + scroll_delta);
976  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
977
978  EXPECT_EQ(ET_GESTURE_SCROLL_UPDATE, GetMostRecentGestureEventType());
979  GestureEventData gesture = GetMostRecentGestureEvent();
980  EXPECT_EQ(0, gesture.details.scroll_x());
981  EXPECT_EQ(scroll_delta, gesture.details.scroll_y());
982  EXPECT_EQ(1, gesture.details.touch_points());
983}
984
985// Verify that movement within the touch slop region does not generate a scroll,
986// and that the slop region is correct even when using fractional coordinates.
987TEST_F(GestureProviderTest, NoScrollWithinTouchSlop) {
988  const float touch_slop = GetTouchSlop();
989  const float scale_factor = 2.5f;
990  const int touch_slop_pixels = static_cast<int>(scale_factor * touch_slop);
991
992  base::TimeTicks event_time = base::TimeTicks::Now();
993
994  MockMotionEvent event =
995      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
996  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
997
998  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
999                            MotionEvent::ACTION_MOVE,
1000                            kFakeCoordX + touch_slop_pixels / scale_factor,
1001                            kFakeCoordY);
1002  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1003  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
1004
1005  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
1006                            MotionEvent::ACTION_MOVE,
1007                            kFakeCoordX,
1008                            kFakeCoordY + touch_slop_pixels / scale_factor);
1009  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1010  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
1011
1012  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
1013                            MotionEvent::ACTION_MOVE,
1014                            kFakeCoordX - touch_slop_pixels / scale_factor,
1015                            kFakeCoordY);
1016  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1017  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
1018
1019  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
1020                            MotionEvent::ACTION_MOVE,
1021                            kFakeCoordX,
1022                            kFakeCoordY - touch_slop_pixels / scale_factor);
1023  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1024  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
1025
1026  event =
1027      ObtainMotionEvent(event_time + kOneMicrosecond * 2,
1028                        MotionEvent::ACTION_MOVE,
1029                        kFakeCoordX,
1030                        kFakeCoordY + (touch_slop_pixels + 1.f) / scale_factor);
1031  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1032  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
1033}
1034
1035TEST_F(GestureProviderTest, NoDoubleTapWhenExplicitlyDisabled) {
1036  // Ensure that double-tap gestures can be disabled.
1037  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(false);
1038
1039  base::TimeTicks event_time = base::TimeTicks::Now();
1040  MockMotionEvent event = ObtainMotionEvent(
1041      event_time, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
1042  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1043  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1044
1045  event = ObtainMotionEvent(event_time + kOneMicrosecond,
1046                            MotionEvent::ACTION_UP,
1047                            kFakeCoordX,
1048                            kFakeCoordY);
1049  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1050  EXPECT_EQ(ET_GESTURE_TAP, GetMostRecentGestureEventType());
1051
1052  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
1053                            MotionEvent::ACTION_DOWN,
1054                            kFakeCoordX,
1055                            kFakeCoordY);
1056  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1057  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1058
1059  event = ObtainMotionEvent(event_time + kOneMicrosecond * 3,
1060                            MotionEvent::ACTION_UP,
1061                            kFakeCoordX,
1062                            kFakeCoordY);
1063  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1064  EXPECT_EQ(ET_GESTURE_TAP, GetMostRecentGestureEventType());
1065
1066  // Ensure that double-tap gestures can be interrupted.
1067  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(true);
1068
1069  event_time = base::TimeTicks::Now();
1070  event = ObtainMotionEvent(
1071      event_time, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
1072  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1073  EXPECT_EQ(5U, GetReceivedGestureCount());
1074
1075  event = ObtainMotionEvent(event_time + kOneMicrosecond,
1076                            MotionEvent::ACTION_UP,
1077                            kFakeCoordX,
1078                            kFakeCoordY);
1079  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1080  EXPECT_EQ(ET_GESTURE_TAP_UNCONFIRMED, GetMostRecentGestureEventType());
1081
1082  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(false);
1083  EXPECT_EQ(ET_GESTURE_TAP, GetMostRecentGestureEventType());
1084
1085  // Ensure that double-tap gestures can be resumed.
1086  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(true);
1087
1088  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
1089                            MotionEvent::ACTION_DOWN,
1090                            kFakeCoordX,
1091                            kFakeCoordY);
1092  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1093  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1094
1095  event = ObtainMotionEvent(event_time + kOneMicrosecond * 3,
1096                            MotionEvent::ACTION_UP,
1097                            kFakeCoordX,
1098                            kFakeCoordY);
1099  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1100  EXPECT_EQ(ET_GESTURE_TAP_UNCONFIRMED, GetMostRecentGestureEventType());
1101
1102  event = ObtainMotionEvent(event_time + kOneMicrosecond * 4,
1103                            MotionEvent::ACTION_DOWN,
1104                            kFakeCoordX,
1105                            kFakeCoordY);
1106  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1107  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1108
1109  event = ObtainMotionEvent(event_time + kOneMicrosecond * 5,
1110                            MotionEvent::ACTION_UP,
1111                            kFakeCoordX,
1112                            kFakeCoordY);
1113  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1114  EXPECT_EQ(ET_GESTURE_DOUBLE_TAP, GetMostRecentGestureEventType());
1115}
1116
1117TEST_F(GestureProviderTest, NoDelayedTapWhenDoubleTapSupportToggled) {
1118  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(true);
1119
1120  base::TimeTicks event_time = base::TimeTicks::Now();
1121  MockMotionEvent event = ObtainMotionEvent(
1122      event_time, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
1123  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1124  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1125  EXPECT_EQ(1U, GetReceivedGestureCount());
1126
1127  event = ObtainMotionEvent(event_time + kOneMicrosecond,
1128                            MotionEvent::ACTION_UP,
1129                            kFakeCoordX,
1130                            kFakeCoordY);
1131  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1132  EXPECT_EQ(ET_GESTURE_TAP_UNCONFIRMED, GetMostRecentGestureEventType());
1133  EXPECT_EQ(2U, GetReceivedGestureCount());
1134
1135  // Disabling double-tap during the tap timeout should flush the delayed tap.
1136  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(false);
1137  EXPECT_EQ(ET_GESTURE_TAP, GetMostRecentGestureEventType());
1138  EXPECT_EQ(3U, GetReceivedGestureCount());
1139
1140  // No further timeout gestures should arrive.
1141  const base::TimeDelta long_press_timeout =
1142      GetLongPressTimeout() + GetShowPressTimeout() + kOneMicrosecond;
1143  RunTasksAndWait(long_press_timeout);
1144  EXPECT_EQ(3U, GetReceivedGestureCount());
1145}
1146
1147TEST_F(GestureProviderTest, NoDoubleTapDragZoomWhenDisabledOnPlatform) {
1148  const base::TimeTicks down_time_1 = TimeTicks::Now();
1149  const base::TimeTicks down_time_2 = down_time_1 + kOneMicrosecond * 2;
1150
1151  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(false);
1152
1153  MockMotionEvent event =
1154      ObtainMotionEvent(down_time_1, MotionEvent::ACTION_DOWN);
1155  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1156
1157  event = ObtainMotionEvent(down_time_1 + kOneMicrosecond,
1158                            MotionEvent::ACTION_UP,
1159                            kFakeCoordX,
1160                            kFakeCoordY);
1161  gesture_provider_->OnTouchEvent(event);
1162
1163  event = ObtainMotionEvent(
1164      down_time_2, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
1165  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1166
1167  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond,
1168                            MotionEvent::ACTION_MOVE,
1169                            kFakeCoordX,
1170                            kFakeCoordY + 100);
1171
1172  // The move should become a scroll, as doubletap drag zoom is disabled.
1173  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1174  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
1175  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_PINCH_BEGIN));
1176
1177  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 2,
1178                            MotionEvent::ACTION_MOVE,
1179                            kFakeCoordX,
1180                            kFakeCoordY + 200);
1181  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1182  EXPECT_EQ(ET_GESTURE_SCROLL_UPDATE, GetMostRecentGestureEventType());
1183  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1184  EXPECT_EQ(down_time_2 + kOneMicrosecond * 2,
1185            GetMostRecentGestureEvent().time);
1186  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_PINCH_UPDATE));
1187
1188  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 3,
1189                            MotionEvent::ACTION_UP,
1190                            kFakeCoordX,
1191                            kFakeCoordY + 200);
1192  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1193  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_PINCH_END));
1194}
1195
1196// Verify that double tap drag zoom feature is not invoked when the gesture
1197// handler is told to disable double tap gesture detection.
1198// The second tap sequence should be treated just as the first would be.
1199TEST_F(GestureProviderTest, NoDoubleTapDragZoomWhenDisabledOnPage) {
1200  const base::TimeTicks down_time_1 = TimeTicks::Now();
1201  const base::TimeTicks down_time_2 = down_time_1 + kOneMicrosecond * 2;
1202
1203  gesture_provider_->SetDoubleTapSupportForPageEnabled(false);
1204
1205  MockMotionEvent event =
1206      ObtainMotionEvent(down_time_1, MotionEvent::ACTION_DOWN);
1207  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1208
1209  event = ObtainMotionEvent(down_time_1 + kOneMicrosecond,
1210                            MotionEvent::ACTION_UP,
1211                            kFakeCoordX,
1212                            kFakeCoordY);
1213  gesture_provider_->OnTouchEvent(event);
1214
1215  event = ObtainMotionEvent(
1216      down_time_2, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
1217  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1218
1219  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond,
1220                            MotionEvent::ACTION_MOVE,
1221                            kFakeCoordX,
1222                            kFakeCoordY + 100);
1223
1224  // The move should become a scroll, as double tap drag zoom is disabled.
1225  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1226  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
1227  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_PINCH_BEGIN));
1228
1229  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 2,
1230                            MotionEvent::ACTION_MOVE,
1231                            kFakeCoordX,
1232                            kFakeCoordY + 200);
1233  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1234  EXPECT_EQ(ET_GESTURE_SCROLL_UPDATE, GetMostRecentGestureEventType());
1235  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1236  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_PINCH_UPDATE));
1237
1238  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 3,
1239                            MotionEvent::ACTION_UP,
1240                            kFakeCoordX,
1241                            kFakeCoordY + 200);
1242  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1243  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_PINCH_END));
1244}
1245
1246// Verify that updating double tap support during a double tap drag zoom
1247// disables double tap detection after the gesture has ended.
1248TEST_F(GestureProviderTest, FixedPageScaleDuringDoubleTapDragZoom) {
1249  base::TimeTicks down_time_1 = TimeTicks::Now();
1250  base::TimeTicks down_time_2 = down_time_1 + kOneMicrosecond * 2;
1251
1252  gesture_provider_->SetDoubleTapSupportForPageEnabled(true);
1253  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(true);
1254
1255  // Start a double-tap drag gesture.
1256  MockMotionEvent event =
1257      ObtainMotionEvent(down_time_1, MotionEvent::ACTION_DOWN);
1258  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1259  event = ObtainMotionEvent(down_time_1 + kOneMicrosecond,
1260                            MotionEvent::ACTION_UP,
1261                            kFakeCoordX,
1262                            kFakeCoordY);
1263  gesture_provider_->OnTouchEvent(event);
1264  event = ObtainMotionEvent(
1265      down_time_2, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
1266  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1267  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond,
1268                            MotionEvent::ACTION_MOVE,
1269                            kFakeCoordX,
1270                            kFakeCoordY + 100);
1271  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1272  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
1273  EXPECT_EQ(ET_GESTURE_PINCH_BEGIN, GetMostRecentGestureEventType());
1274  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1275
1276  // Simulate setting a fixed page scale (or a mobile viewport);
1277  // this should not disrupt the current double-tap gesture.
1278  gesture_provider_->SetDoubleTapSupportForPageEnabled(false);
1279
1280  // Double tap zoom updates should continue.
1281  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 2,
1282                            MotionEvent::ACTION_MOVE,
1283                            kFakeCoordX,
1284                            kFakeCoordY + 200);
1285  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1286  EXPECT_EQ(ET_GESTURE_PINCH_UPDATE, GetMostRecentGestureEventType());
1287  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1288  EXPECT_LT(1.f, GetMostRecentGestureEvent().details.scale());
1289  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 3,
1290                            MotionEvent::ACTION_UP,
1291                            kFakeCoordX,
1292                            kFakeCoordY + 200);
1293  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1294  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_PINCH_END));
1295  EXPECT_EQ(ET_GESTURE_SCROLL_END, GetMostRecentGestureEventType());
1296  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1297
1298  // The double-tap gesture has finished, but the page scale is fixed.
1299  // The same event sequence should not generate any double tap getsures.
1300  gestures_.clear();
1301  down_time_1 += kOneMicrosecond * 40;
1302  down_time_2 += kOneMicrosecond * 40;
1303
1304  // Start a double-tap drag gesture.
1305  event = ObtainMotionEvent(down_time_1, MotionEvent::ACTION_DOWN);
1306  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1307  event = ObtainMotionEvent(down_time_1 + kOneMicrosecond,
1308                            MotionEvent::ACTION_UP,
1309                            kFakeCoordX,
1310                            kFakeCoordY);
1311  gesture_provider_->OnTouchEvent(event);
1312  event = ObtainMotionEvent(
1313      down_time_2, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
1314  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1315  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond,
1316                            MotionEvent::ACTION_MOVE,
1317                            kFakeCoordX,
1318                            kFakeCoordY + 100);
1319  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1320  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
1321  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_PINCH_BEGIN));
1322
1323  // Double tap zoom updates should not be sent.
1324  // Instead, the second tap drag becomes a scroll gesture sequence.
1325  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 2,
1326                            MotionEvent::ACTION_MOVE,
1327                            kFakeCoordX,
1328                            kFakeCoordY + 200);
1329  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1330  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_UPDATE));
1331  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_PINCH_UPDATE));
1332  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 3,
1333                            MotionEvent::ACTION_UP,
1334                            kFakeCoordX,
1335                            kFakeCoordY + 200);
1336  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1337  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_PINCH_END));
1338}
1339
1340// Verify that pinch zoom sends the proper event sequence.
1341TEST_F(GestureProviderTest, PinchZoom) {
1342  base::TimeTicks event_time = base::TimeTicks::Now();
1343  const float touch_slop = GetTouchSlop();
1344  int motion_event_id = 0;
1345
1346  gesture_provider_->SetDoubleTapSupportForPageEnabled(false);
1347  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(true);
1348  gesture_provider_->SetMultiTouchZoomSupportEnabled(true);
1349
1350  int secondary_coord_x = kFakeCoordX + 20 * touch_slop;
1351  int secondary_coord_y = kFakeCoordY + 20 * touch_slop;
1352
1353  MockMotionEvent event =
1354      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
1355  event.SetId(++motion_event_id);
1356  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1357  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1358  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1359  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY),
1360            GetMostRecentGestureEvent().details.bounding_box());
1361
1362  // Toggling double-tap support should not take effect until the next sequence.
1363  gesture_provider_->SetDoubleTapSupportForPageEnabled(true);
1364
1365  event = ObtainMotionEvent(event_time,
1366                            MotionEvent::ACTION_POINTER_DOWN,
1367                            kFakeCoordX,
1368                            kFakeCoordY,
1369                            secondary_coord_x,
1370                            secondary_coord_y);
1371  event.SetId(++motion_event_id);
1372
1373  gesture_provider_->OnTouchEvent(event);
1374  EXPECT_EQ(1U, GetReceivedGestureCount());
1375  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1376  EXPECT_EQ(BoundsForSingleMockTouchAtLocation(kFakeCoordX, kFakeCoordY),
1377            GetMostRecentGestureEvent().details.bounding_box());
1378
1379  secondary_coord_x += 5 * touch_slop;
1380  secondary_coord_y += 5 * touch_slop;
1381  event = ObtainMotionEvent(event_time,
1382                            MotionEvent::ACTION_MOVE,
1383                            kFakeCoordX,
1384                            kFakeCoordY,
1385                            secondary_coord_x,
1386                            secondary_coord_y);
1387  event.SetId(++motion_event_id);
1388
1389  // Toggling double-tap support should not take effect until the next sequence.
1390  gesture_provider_->SetDoubleTapSupportForPageEnabled(false);
1391
1392  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1393  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
1394  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1395  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_PINCH_BEGIN));
1396  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
1397  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_UPDATE));
1398  EXPECT_EQ(
1399      gfx::RectF(kFakeCoordX - kMockTouchRadius,
1400                 kFakeCoordY - kMockTouchRadius,
1401                 secondary_coord_x - kFakeCoordX + kMockTouchRadius * 2,
1402                 secondary_coord_y - kFakeCoordY + kMockTouchRadius * 2),
1403      GetMostRecentGestureEvent().details.bounding_box());
1404
1405  secondary_coord_x += 2 * touch_slop;
1406  secondary_coord_y += 2 * touch_slop;
1407  event = ObtainMotionEvent(event_time,
1408                            MotionEvent::ACTION_MOVE,
1409                            kFakeCoordX,
1410                            kFakeCoordY,
1411                            secondary_coord_x,
1412                            secondary_coord_y);
1413  event.SetId(++motion_event_id);
1414
1415  // Toggling double-tap support should not take effect until the next sequence.
1416  gesture_provider_->SetDoubleTapSupportForPageEnabled(true);
1417
1418  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1419  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
1420  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_UPDATE));
1421  EXPECT_EQ(ET_GESTURE_PINCH_UPDATE, GetMostRecentGestureEventType());
1422  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1423  EXPECT_LT(1.f, GetMostRecentGestureEvent().details.scale());
1424  EXPECT_EQ(
1425      gfx::RectF(kFakeCoordX - kMockTouchRadius,
1426                 kFakeCoordY - kMockTouchRadius,
1427                 secondary_coord_x - kFakeCoordX + kMockTouchRadius * 2,
1428                 secondary_coord_y - kFakeCoordY + kMockTouchRadius * 2),
1429      GetMostRecentGestureEvent().details.bounding_box());
1430
1431  event = ObtainMotionEvent(event_time,
1432                            MotionEvent::ACTION_POINTER_UP,
1433                            kFakeCoordX,
1434                            kFakeCoordY,
1435                            secondary_coord_x,
1436                            secondary_coord_y);
1437  event.SetId(++motion_event_id);
1438
1439  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1440  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
1441  EXPECT_EQ(ET_GESTURE_PINCH_END, GetMostRecentGestureEventType());
1442  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1443  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_SCROLL_END));
1444  EXPECT_EQ(
1445      gfx::RectF(kFakeCoordX - kMockTouchRadius,
1446                 kFakeCoordY - kMockTouchRadius,
1447                 secondary_coord_x - kFakeCoordX + kMockTouchRadius * 2,
1448                 secondary_coord_y - kFakeCoordY + kMockTouchRadius * 2),
1449      GetMostRecentGestureEvent().details.bounding_box());
1450
1451  event = ObtainMotionEvent(event_time, MotionEvent::ACTION_UP);
1452  gesture_provider_->OnTouchEvent(event);
1453  EXPECT_EQ(ET_GESTURE_SCROLL_END, GetMostRecentGestureEventType());
1454  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1455  EXPECT_EQ(gfx::RectF(kFakeCoordX - kMockTouchRadius,
1456                       kFakeCoordY - kMockTouchRadius,
1457                       kMockTouchRadius * 2,
1458                       kMockTouchRadius * 2),
1459            GetMostRecentGestureEvent().details.bounding_box());
1460}
1461
1462// Verify that multi-finger swipe sends the proper event sequence.
1463TEST_F(GestureProviderTest, MultiFingerSwipe) {
1464  EnableSwipe();
1465  gesture_provider_->SetMultiTouchZoomSupportEnabled(false);
1466  const float min_swipe_velocity = GetMinSwipeVelocity();
1467
1468  // One finger - swipe right
1469  OneFingerSwipe(2 * min_swipe_velocity, 0);
1470  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SWIPE));
1471  EXPECT_TRUE(GetMostRecentGestureEvent().details.swipe_right());
1472  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1473  ResetGestureDetection();
1474
1475  // One finger - swipe left
1476  OneFingerSwipe(-2 * min_swipe_velocity, 0);
1477  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SWIPE));
1478  EXPECT_TRUE(GetMostRecentGestureEvent().details.swipe_left());
1479  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1480  ResetGestureDetection();
1481
1482  // One finger - swipe down
1483  OneFingerSwipe(0, 2 * min_swipe_velocity);
1484  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SWIPE));
1485  EXPECT_TRUE(GetMostRecentGestureEvent().details.swipe_down());
1486  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1487  ResetGestureDetection();
1488
1489  // One finger - swipe up
1490  OneFingerSwipe(0, -2 * min_swipe_velocity);
1491  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SWIPE));
1492  EXPECT_TRUE(GetMostRecentGestureEvent().details.swipe_up());
1493  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1494  ResetGestureDetection();
1495
1496  // Two fingers
1497  // Swipe right.
1498  TwoFingerSwipe(min_swipe_velocity * 2, 0, min_swipe_velocity * 2, 0);
1499  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SWIPE));
1500  EXPECT_TRUE(GetMostRecentGestureEvent().details.swipe_right());
1501  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1502  ResetGestureDetection();
1503
1504  // Swipe left.
1505  TwoFingerSwipe(-min_swipe_velocity * 2, 0, -min_swipe_velocity * 2, 0);
1506  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SWIPE));
1507  EXPECT_TRUE(GetMostRecentGestureEvent().details.swipe_left());
1508  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1509  ResetGestureDetection();
1510
1511  // No swipe with different touch directions.
1512  TwoFingerSwipe(min_swipe_velocity * 2, 0, -min_swipe_velocity * 2, 0);
1513  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_SWIPE));
1514  ResetGestureDetection();
1515
1516  // No swipe without a dominant direction.
1517  TwoFingerSwipe(min_swipe_velocity * 2,
1518                 min_swipe_velocity * 2,
1519                 min_swipe_velocity * 2,
1520                 min_swipe_velocity * 2);
1521  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_SWIPE));
1522  ResetGestureDetection();
1523
1524  // Swipe down with non-zero velocities on both axes and dominant direction.
1525  TwoFingerSwipe(-min_swipe_velocity,
1526                 min_swipe_velocity * 4,
1527                 -min_swipe_velocity,
1528                 min_swipe_velocity * 4);
1529  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SWIPE));
1530  EXPECT_TRUE(GetMostRecentGestureEvent().details.swipe_down());
1531  EXPECT_FALSE(GetMostRecentGestureEvent().details.swipe_left());
1532  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1533  ResetGestureDetection();
1534
1535  // Swipe up with non-zero velocities on both axes.
1536  TwoFingerSwipe(min_swipe_velocity,
1537                 -min_swipe_velocity * 4,
1538                 min_swipe_velocity,
1539                 -min_swipe_velocity * 4);
1540  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SWIPE));
1541  EXPECT_TRUE(GetMostRecentGestureEvent().details.swipe_up());
1542  EXPECT_FALSE(GetMostRecentGestureEvent().details.swipe_right());
1543  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1544  ResetGestureDetection();
1545
1546  // No swipe without sufficient velocity.
1547  TwoFingerSwipe(min_swipe_velocity / 2, 0, 0, 0);
1548  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_SWIPE));
1549  ResetGestureDetection();
1550
1551  // Swipe up with one small and one medium velocity in slightly different but
1552  // not opposing directions.
1553  TwoFingerSwipe(min_swipe_velocity / 2,
1554                 min_swipe_velocity / 2,
1555                 0,
1556                 min_swipe_velocity * 2);
1557  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SWIPE));
1558  EXPECT_TRUE(GetMostRecentGestureEvent().details.swipe_down());
1559  EXPECT_FALSE(GetMostRecentGestureEvent().details.swipe_right());
1560  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1561  ResetGestureDetection();
1562
1563  // No swipe in orthogonal directions.
1564  TwoFingerSwipe(min_swipe_velocity * 2, 0, 0, min_swipe_velocity * 7);
1565  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_SWIPE));
1566  ResetGestureDetection();
1567
1568  // Three finger swipe in same directions.
1569  ThreeFingerSwipe(min_swipe_velocity * 2,
1570                   0,
1571                   min_swipe_velocity * 3,
1572                   0,
1573                   min_swipe_velocity * 4,
1574                   0);
1575  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SWIPE));
1576  EXPECT_TRUE(GetMostRecentGestureEvent().details.swipe_right());
1577  EXPECT_EQ(3, GetMostRecentGestureEvent().details.touch_points());
1578  ResetGestureDetection();
1579
1580  // No three finger swipe in different directions.
1581  ThreeFingerSwipe(min_swipe_velocity * 2,
1582                   0,
1583                   0,
1584                   min_swipe_velocity * 3,
1585                   min_swipe_velocity * 4,
1586                   0);
1587  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_SWIPE));
1588}
1589
1590// Verify that the timer of LONG_PRESS will be cancelled when scrolling begins
1591// so LONG_PRESS and LONG_TAP won't be triggered.
1592TEST_F(GestureProviderTest, GesturesCancelledAfterLongPressCausesLostFocus) {
1593  base::TimeTicks event_time = base::TimeTicks::Now();
1594
1595  MockMotionEvent event =
1596      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
1597  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1598
1599  const base::TimeDelta long_press_timeout =
1600      GetLongPressTimeout() + GetShowPressTimeout() + kOneMicrosecond;
1601  RunTasksAndWait(long_press_timeout);
1602  EXPECT_EQ(ET_GESTURE_LONG_PRESS, GetMostRecentGestureEventType());
1603  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1604
1605  EXPECT_TRUE(CancelActiveTouchSequence());
1606  EXPECT_FALSE(HasDownEvent());
1607
1608  event = ObtainMotionEvent(event_time + long_press_timeout,
1609                            MotionEvent::ACTION_UP);
1610  gesture_provider_->OnTouchEvent(event);
1611  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_LONG_TAP));
1612}
1613
1614// Verify that inserting a touch cancel event will trigger proper touch and
1615// gesture sequence cancellation.
1616TEST_F(GestureProviderTest, CancelActiveTouchSequence) {
1617  base::TimeTicks event_time = base::TimeTicks::Now();
1618  int motion_event_id = 0;
1619
1620  EXPECT_FALSE(CancelActiveTouchSequence());
1621  EXPECT_EQ(0U, GetReceivedGestureCount());
1622
1623  MockMotionEvent event =
1624      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
1625  event.SetId(++motion_event_id);
1626  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1627  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1628  EXPECT_EQ(motion_event_id, GetMostRecentGestureEvent().motion_event_id);
1629  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1630
1631  ASSERT_TRUE(CancelActiveTouchSequence());
1632  EXPECT_FALSE(HasDownEvent());
1633
1634  // Subsequent MotionEvent's are dropped until ACTION_DOWN.
1635  event = ObtainMotionEvent(event_time + kOneMicrosecond,
1636                            MotionEvent::ACTION_MOVE);
1637  EXPECT_FALSE(gesture_provider_->OnTouchEvent(event));
1638
1639  event = ObtainMotionEvent(event_time + kOneMicrosecond * 2,
1640                            MotionEvent::ACTION_UP);
1641  EXPECT_FALSE(gesture_provider_->OnTouchEvent(event));
1642
1643  event = ObtainMotionEvent(event_time + kOneMicrosecond * 3,
1644                            MotionEvent::ACTION_DOWN);
1645  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1646  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1647  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1648}
1649
1650TEST_F(GestureProviderTest, DoubleTapDragZoomCancelledOnSecondaryPointerDown) {
1651  const base::TimeTicks down_time_1 = TimeTicks::Now();
1652  const base::TimeTicks down_time_2 = down_time_1 + kOneMicrosecond * 2;
1653
1654  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(true);
1655
1656  MockMotionEvent event =
1657      ObtainMotionEvent(down_time_1, MotionEvent::ACTION_DOWN);
1658  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1659  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1660  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1661
1662  event =
1663      ObtainMotionEvent(down_time_1 + kOneMicrosecond, MotionEvent::ACTION_UP);
1664  gesture_provider_->OnTouchEvent(event);
1665  EXPECT_EQ(ET_GESTURE_TAP_UNCONFIRMED, GetMostRecentGestureEventType());
1666  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1667
1668  event = ObtainMotionEvent(down_time_2, MotionEvent::ACTION_DOWN);
1669  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1670  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1671  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1672
1673  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond,
1674                            MotionEvent::ACTION_MOVE,
1675                            kFakeCoordX,
1676                            kFakeCoordY - 30);
1677  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1678  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
1679  EXPECT_EQ(ET_GESTURE_PINCH_BEGIN, GetMostRecentGestureEventType());
1680  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1681
1682  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 2,
1683                            MotionEvent::ACTION_POINTER_DOWN,
1684                            kFakeCoordX,
1685                            kFakeCoordY - 30,
1686                            kFakeCoordX + 50,
1687                            kFakeCoordY + 50);
1688  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1689  EXPECT_EQ(ET_GESTURE_PINCH_END, GetMostRecentGestureEventType());
1690  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1691
1692  const size_t gesture_count = GetReceivedGestureCount();
1693  event = ObtainMotionEvent(down_time_2 + kOneMicrosecond * 3,
1694                            MotionEvent::ACTION_POINTER_UP,
1695                            kFakeCoordX,
1696                            kFakeCoordY - 30,
1697                            kFakeCoordX + 50,
1698                            kFakeCoordY + 50);
1699  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1700  EXPECT_EQ(gesture_count, GetReceivedGestureCount());
1701
1702  event = ObtainMotionEvent(down_time_2 + kOneSecond,
1703                            MotionEvent::ACTION_UP);
1704  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1705  EXPECT_EQ(gesture_count + 1, GetReceivedGestureCount());
1706  EXPECT_EQ(ET_GESTURE_SCROLL_END, GetMostRecentGestureEventType());
1707  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1708}
1709
1710// Verify that gesture begin and gesture end events are dispatched correctly.
1711TEST_F(GestureProviderTest, GestureBeginAndEnd) {
1712  EnableBeginEndTypes();
1713  base::TimeTicks event_time = base::TimeTicks::Now();
1714
1715  EXPECT_EQ(0U, GetReceivedGestureCount());
1716  MockMotionEvent event =
1717      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
1718  event.pointer_count = 1;
1719  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1720  EXPECT_EQ(ET_GESTURE_BEGIN, GetReceivedGesture(0).type);
1721  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1722  EXPECT_EQ(2U, GetReceivedGestureCount());
1723  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1724  EXPECT_EQ(gfx::RectF(kFakeCoordX - kMockTouchRadius,
1725                       kFakeCoordY - kMockTouchRadius,
1726                       kMockTouchRadius * 2,
1727                       kMockTouchRadius * 2),
1728            GetMostRecentGestureEvent().details.bounding_box());
1729
1730  event = ObtainMotionEvent(event_time, MotionEvent::ACTION_POINTER_DOWN);
1731  event.pointer_count = 2;
1732  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1733  EXPECT_EQ(ET_GESTURE_BEGIN, GetMostRecentGestureEventType());
1734  EXPECT_EQ(3U, GetReceivedGestureCount());
1735  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1736
1737  event = ObtainMotionEvent(event_time, MotionEvent::ACTION_POINTER_DOWN);
1738  event.pointer_count = 3;
1739  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1740  EXPECT_EQ(ET_GESTURE_BEGIN, GetMostRecentGestureEventType());
1741  EXPECT_EQ(4U, GetReceivedGestureCount());
1742  EXPECT_EQ(3, GetMostRecentGestureEvent().details.touch_points());
1743
1744  event = ObtainMotionEvent(event_time, MotionEvent::ACTION_POINTER_UP);
1745  event.pointer_count = 2;
1746  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1747  EXPECT_EQ(ET_GESTURE_END, GetMostRecentGestureEventType());
1748  EXPECT_EQ(5U, GetReceivedGestureCount());
1749  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1750
1751  event = ObtainMotionEvent(event_time, MotionEvent::ACTION_POINTER_DOWN);
1752  event.pointer_count = 3;
1753  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1754  EXPECT_EQ(ET_GESTURE_BEGIN, GetMostRecentGestureEventType());
1755  EXPECT_EQ(6U, GetReceivedGestureCount());
1756  EXPECT_EQ(3, GetMostRecentGestureEvent().details.touch_points());
1757
1758  event = ObtainMotionEvent(event_time, MotionEvent::ACTION_POINTER_UP);
1759  event.pointer_count = 2;
1760  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1761  EXPECT_EQ(ET_GESTURE_END, GetMostRecentGestureEventType());
1762  EXPECT_EQ(7U, GetReceivedGestureCount());
1763  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
1764
1765  event = ObtainMotionEvent(event_time, MotionEvent::ACTION_POINTER_UP);
1766  event.pointer_count = 1;
1767  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1768  EXPECT_EQ(ET_GESTURE_END, GetMostRecentGestureEventType());
1769  EXPECT_EQ(8U, GetReceivedGestureCount());
1770  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1771
1772  event = ObtainMotionEvent(event_time, MotionEvent::ACTION_UP);
1773  event.pointer_count = 1;
1774  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1775  EXPECT_EQ(ET_GESTURE_END, GetMostRecentGestureEventType());
1776  EXPECT_EQ(9U, GetReceivedGestureCount());
1777  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1778
1779  event = ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
1780  event.pointer_count = 1;
1781  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1782  EXPECT_EQ(ET_GESTURE_BEGIN, GetReceivedGesture(9).type);
1783  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1784  EXPECT_EQ(11U, GetReceivedGestureCount());
1785  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1786
1787  event = ObtainMotionEvent(event_time, MotionEvent::ACTION_CANCEL);
1788  event.pointer_count = 1;
1789  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1790  EXPECT_EQ(ET_GESTURE_END, GetMostRecentGestureEventType());
1791  EXPECT_EQ(12U, GetReceivedGestureCount());
1792  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1793}
1794
1795
1796// Test a simple two finger tap
1797TEST_F(GestureProviderTest, TwoFingerTap) {
1798  // The time between ACTION_POINTER_DOWN and ACTION_POINTER_UP must be <= the
1799  // two finger tap delay.
1800  EnableTwoFingerTap(kMaxTwoFingerTapSeparation, base::TimeDelta());
1801  const float scaled_touch_slop = GetTouchSlop();
1802
1803  base::TimeTicks event_time = base::TimeTicks::Now();
1804
1805  MockMotionEvent event =
1806      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN, 0, 0);
1807  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1808
1809  event = ObtainMotionEvent(event_time,
1810                            MotionEvent::ACTION_MOVE,
1811                            0,
1812                            scaled_touch_slop / 2);
1813
1814  event = ObtainMotionEvent(event_time,
1815                            MotionEvent::ACTION_POINTER_DOWN,
1816                            0,
1817                            0,
1818                            kMaxTwoFingerTapSeparation / 2,
1819                            0);
1820  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1821
1822  event =
1823      ObtainMotionEvent(event_time,
1824                        MotionEvent::ACTION_MOVE,
1825                        0,
1826                        -scaled_touch_slop / 2,
1827                        kMaxTwoFingerTapSeparation / 2 + scaled_touch_slop / 2,
1828                        0);
1829  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1830
1831  event = ObtainMotionEvent(event_time,
1832                            MotionEvent::ACTION_POINTER_UP,
1833                            0,
1834                            0,
1835                            kMaxTwoFingerTapSeparation,
1836                            0);
1837  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1838
1839  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetReceivedGesture(0).type);
1840  EXPECT_EQ(ET_GESTURE_SCROLL_BEGIN, GetReceivedGesture(1).type);
1841  EXPECT_EQ(ET_GESTURE_TWO_FINGER_TAP, GetReceivedGesture(2).type);
1842  EXPECT_EQ(3U, GetReceivedGestureCount());
1843
1844  EXPECT_EQ(kMockTouchRadius * 2,
1845            GetReceivedGesture(2).details.first_finger_width());
1846  EXPECT_EQ(kMockTouchRadius * 2,
1847            GetReceivedGesture(2).details.first_finger_height());
1848}
1849
1850// Test preventing a two finger tap via finger movement.
1851TEST_F(GestureProviderTest, TwoFingerTapCancelledByFingerMovement) {
1852  EnableTwoFingerTap(kMaxTwoFingerTapSeparation, base::TimeDelta());
1853  const float scaled_touch_slop = GetTouchSlop();
1854  base::TimeTicks event_time = base::TimeTicks::Now();
1855
1856  MockMotionEvent event = ObtainMotionEvent(
1857      event_time, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
1858  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1859
1860  event = ObtainMotionEvent(event_time,
1861                            MotionEvent::ACTION_POINTER_DOWN,
1862                            kFakeCoordX,
1863                            kFakeCoordY,
1864                            kFakeCoordX,
1865                            kFakeCoordY);
1866  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1867
1868  event = ObtainMotionEvent(event_time,
1869                            MotionEvent::ACTION_MOVE,
1870                            kFakeCoordX,
1871                            kFakeCoordY,
1872                            kFakeCoordX + scaled_touch_slop + 0.1,
1873                            kFakeCoordY);
1874  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1875
1876  event = ObtainMotionEvent(event_time,
1877                            MotionEvent::ACTION_POINTER_UP,
1878                            kFakeCoordX,
1879                            kFakeCoordY,
1880                            kFakeCoordX,
1881                            kFakeCoordY);
1882  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1883
1884  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetReceivedGesture(0).type);
1885  EXPECT_EQ(ET_GESTURE_SCROLL_BEGIN, GetReceivedGesture(1).type);
1886  EXPECT_EQ(2U, GetReceivedGestureCount());
1887}
1888
1889// Test preventing a two finger tap by waiting too long before releasing the
1890// secondary pointer.
1891TEST_F(GestureProviderTest, TwoFingerTapCancelledByDelay) {
1892  base::TimeDelta two_finger_tap_timeout = kOneSecond;
1893  EnableTwoFingerTap(kMaxTwoFingerTapSeparation, two_finger_tap_timeout);
1894  base::TimeTicks event_time = base::TimeTicks::Now();
1895
1896  MockMotionEvent event = ObtainMotionEvent(
1897      event_time, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
1898  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1899
1900  event = ObtainMotionEvent(event_time,
1901                            MotionEvent::ACTION_MOVE,
1902                            kFakeCoordX,
1903                            kFakeCoordY);
1904
1905  event = ObtainMotionEvent(event_time,
1906                            MotionEvent::ACTION_POINTER_DOWN,
1907                            kFakeCoordX,
1908                            kFakeCoordY,
1909                            kFakeCoordX + kMaxTwoFingerTapSeparation / 2,
1910                            kFakeCoordY);
1911  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1912
1913  event = ObtainMotionEvent(event_time + kOneSecond + kOneMicrosecond,
1914                            MotionEvent::ACTION_POINTER_UP,
1915                            kFakeCoordX,
1916                            kFakeCoordY,
1917                            kFakeCoordX + kMaxTwoFingerTapSeparation / 2,
1918                            kFakeCoordY);
1919  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1920
1921  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetReceivedGesture(0).type);
1922  EXPECT_EQ(1U, GetReceivedGestureCount());
1923}
1924
1925// Test preventing a two finger tap by pressing the secondary pointer too far
1926// from the first
1927TEST_F(GestureProviderTest, TwoFingerTapCancelledByDistanceBetweenPointers) {
1928  EnableTwoFingerTap(kMaxTwoFingerTapSeparation, base::TimeDelta());
1929  base::TimeTicks event_time = base::TimeTicks::Now();
1930
1931  MockMotionEvent event = ObtainMotionEvent(
1932      event_time, MotionEvent::ACTION_DOWN, kFakeCoordX, kFakeCoordY);
1933  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1934
1935  event = ObtainMotionEvent(event_time,
1936                            MotionEvent::ACTION_POINTER_DOWN,
1937                            kFakeCoordX,
1938                            kFakeCoordY,
1939                            kFakeCoordX + kMaxTwoFingerTapSeparation,
1940                            kFakeCoordY);
1941  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1942
1943  event = ObtainMotionEvent(event_time,
1944                            MotionEvent::ACTION_POINTER_UP,
1945                            kFakeCoordX,
1946                            kFakeCoordY,
1947                            kFakeCoordX + kMaxTwoFingerTapSeparation,
1948                            kFakeCoordY);
1949  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1950
1951  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetReceivedGesture(0).type);
1952  EXPECT_EQ(1U, GetReceivedGestureCount());
1953}
1954
1955// Verify that pinch zoom only sends updates which exceed the
1956// min_pinch_update_span_delta.
1957TEST_F(GestureProviderTest, PinchZoomWithThreshold) {
1958  const float kMinPinchUpdateDistance = 5;
1959
1960  base::TimeTicks event_time = base::TimeTicks::Now();
1961  const float touch_slop = GetTouchSlop();
1962
1963  SetMinPinchUpdateSpanDelta(kMinPinchUpdateDistance);
1964  gesture_provider_->SetDoubleTapSupportForPageEnabled(false);
1965  gesture_provider_->SetDoubleTapSupportForPlatformEnabled(true);
1966  gesture_provider_->SetMultiTouchZoomSupportEnabled(true);
1967
1968  int secondary_coord_x = kFakeCoordX + 20 * touch_slop;
1969  int secondary_coord_y = kFakeCoordY + 20 * touch_slop;
1970
1971  // First finger down.
1972  MockMotionEvent event =
1973      ObtainMotionEvent(event_time, MotionEvent::ACTION_DOWN);
1974  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
1975  EXPECT_EQ(ET_GESTURE_TAP_DOWN, GetMostRecentGestureEventType());
1976  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1977
1978  // Second finger down.
1979  event = ObtainMotionEvent(event_time,
1980                            MotionEvent::ACTION_POINTER_DOWN,
1981                            kFakeCoordX,
1982                            kFakeCoordY,
1983                            secondary_coord_x,
1984                            secondary_coord_y);
1985
1986  gesture_provider_->OnTouchEvent(event);
1987  EXPECT_EQ(1U, GetReceivedGestureCount());
1988  EXPECT_EQ(1, GetMostRecentGestureEvent().details.touch_points());
1989
1990  // Move second finger.
1991  secondary_coord_x += 5 * touch_slop;
1992  secondary_coord_y += 5 * touch_slop;
1993  event = ObtainMotionEvent(event_time,
1994                            MotionEvent::ACTION_MOVE,
1995                            kFakeCoordX,
1996                            kFakeCoordY,
1997                            secondary_coord_x,
1998                            secondary_coord_y);
1999
2000  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
2001  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
2002  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_PINCH_BEGIN));
2003  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_PINCH_UPDATE));
2004  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_BEGIN));
2005  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_SCROLL_UPDATE));
2006
2007  // Small move, shouldn't trigger pinch.
2008  event = ObtainMotionEvent(event_time,
2009                            MotionEvent::ACTION_MOVE,
2010                            kFakeCoordX,
2011                            kFakeCoordY,
2012                            secondary_coord_x + kMinPinchUpdateDistance,
2013                            secondary_coord_y);
2014
2015  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
2016  EXPECT_FALSE(HasReceivedGesture(ET_GESTURE_PINCH_UPDATE));
2017  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
2018
2019  // Small move, but combined with the previous move, should trigger pinch. We
2020  // need to overshoot kMinPinchUpdateDistance by a fair bit, as the span
2021  // calculation factors in touch radius.
2022  const float kOvershootMinPinchUpdateDistance = 3;
2023  event = ObtainMotionEvent(event_time,
2024                            MotionEvent::ACTION_MOVE,
2025                            kFakeCoordX,
2026                            kFakeCoordY,
2027                            secondary_coord_x + kMinPinchUpdateDistance +
2028                                kOvershootMinPinchUpdateDistance,
2029                            secondary_coord_y);
2030
2031  EXPECT_TRUE(gesture_provider_->OnTouchEvent(event));
2032  EXPECT_TRUE(HasReceivedGesture(ET_GESTURE_PINCH_UPDATE));
2033  EXPECT_EQ(2, GetMostRecentGestureEvent().details.touch_points());
2034}
2035
2036}  // namespace ui
2037