OLD | NEW |
| (Empty) |
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 "ui/events/gestures/gesture_provider_aura.h" | |
6 | |
7 #include "base/auto_reset.h" | |
8 #include "base/logging.h" | |
9 #include "ui/events/event.h" | |
10 #include "ui/events/gesture_detection/gesture_config_helper.h" | |
11 #include "ui/events/gesture_detection/gesture_event_data.h" | |
12 #include "ui/events/gestures/gesture_configuration.h" | |
13 | |
14 namespace ui { | |
15 | |
16 GestureProviderAura::GestureProviderAura(GestureProviderAuraClient* client) | |
17 : client_(client), | |
18 filtered_gesture_provider_(ui::DefaultGestureProviderConfig(), this), | |
19 handling_event_(false) { | |
20 filtered_gesture_provider_.SetDoubleTapSupportForPlatformEnabled(false); | |
21 } | |
22 | |
23 GestureProviderAura::~GestureProviderAura() {} | |
24 | |
25 bool GestureProviderAura::OnTouchEvent(const TouchEvent& event) { | |
26 int index = pointer_state_.FindPointerIndexOfId(event.touch_id()); | |
27 bool pointer_id_is_active = index != -1; | |
28 | |
29 if (event.type() == ET_TOUCH_PRESSED && pointer_id_is_active) { | |
30 // Ignore touch press events if we already believe the pointer is down. | |
31 return false; | |
32 } else if (event.type() != ET_TOUCH_PRESSED && !pointer_id_is_active) { | |
33 // We could have an active touch stream transfered to us, resulting in touch | |
34 // move or touch up events without associated touch down events. Ignore | |
35 // them. | |
36 return false; | |
37 } | |
38 | |
39 // If this is a touchmove event, and it isn't different from the last | |
40 // event, ignore it. | |
41 if (event.type() == ET_TOUCH_MOVED && | |
42 event.x() == pointer_state_.GetX(index) && | |
43 event.y() == pointer_state_.GetY(index)) { | |
44 return false; | |
45 } | |
46 | |
47 last_touch_event_latency_info_ = *event.latency(); | |
48 pointer_state_.OnTouch(event); | |
49 | |
50 bool result = filtered_gesture_provider_.OnTouchEvent(pointer_state_); | |
51 pointer_state_.CleanupRemovedTouchPoints(event); | |
52 return result; | |
53 } | |
54 | |
55 void GestureProviderAura::OnTouchEventAck(bool event_consumed) { | |
56 DCHECK(pending_gestures_.empty()); | |
57 DCHECK(!handling_event_); | |
58 base::AutoReset<bool> handling_event(&handling_event_, true); | |
59 filtered_gesture_provider_.OnTouchEventAck(event_consumed); | |
60 last_touch_event_latency_info_.Clear(); | |
61 } | |
62 | |
63 void GestureProviderAura::OnGestureEvent( | |
64 const GestureEventData& gesture) { | |
65 GestureEventDetails details = gesture.details; | |
66 details.set_oldest_touch_id(gesture.motion_event_id); | |
67 | |
68 if (gesture.type() == ET_GESTURE_TAP) { | |
69 int tap_count = 1; | |
70 if (previous_tap_ && IsConsideredDoubleTap(*previous_tap_, gesture)) | |
71 tap_count = 1 + (previous_tap_->details.tap_count() % 3); | |
72 details.set_tap_count(tap_count); | |
73 if (!previous_tap_) | |
74 previous_tap_.reset(new GestureEventData(gesture)); | |
75 else | |
76 *previous_tap_ = gesture; | |
77 previous_tap_->details = details; | |
78 } else if (gesture.type() == ET_GESTURE_TAP_CANCEL) { | |
79 previous_tap_.reset(); | |
80 } | |
81 | |
82 scoped_ptr<ui::GestureEvent> event( | |
83 new ui::GestureEvent(gesture.x, | |
84 gesture.y, | |
85 gesture.flags, | |
86 gesture.time - base::TimeTicks(), | |
87 details)); | |
88 | |
89 ui::LatencyInfo* gesture_latency = event->latency(); | |
90 | |
91 gesture_latency->CopyLatencyFrom( | |
92 last_touch_event_latency_info_, | |
93 ui::INPUT_EVENT_LATENCY_ORIGINAL_COMPONENT); | |
94 gesture_latency->CopyLatencyFrom( | |
95 last_touch_event_latency_info_, | |
96 ui::INPUT_EVENT_LATENCY_UI_COMPONENT); | |
97 gesture_latency->CopyLatencyFrom( | |
98 last_touch_event_latency_info_, | |
99 ui::INPUT_EVENT_LATENCY_ACKED_TOUCH_COMPONENT); | |
100 | |
101 if (!handling_event_) { | |
102 // Dispatching event caused by timer. | |
103 client_->OnGestureEvent(event.get()); | |
104 } else { | |
105 // Memory managed by ScopedVector pending_gestures_. | |
106 pending_gestures_.push_back(event.release()); | |
107 } | |
108 } | |
109 | |
110 ScopedVector<GestureEvent>* GestureProviderAura::GetAndResetPendingGestures() { | |
111 if (pending_gestures_.empty()) | |
112 return NULL; | |
113 // Caller is responsible for deleting old_pending_gestures. | |
114 ScopedVector<GestureEvent>* old_pending_gestures = | |
115 new ScopedVector<GestureEvent>(); | |
116 old_pending_gestures->swap(pending_gestures_); | |
117 return old_pending_gestures; | |
118 } | |
119 | |
120 bool GestureProviderAura::IsConsideredDoubleTap( | |
121 const GestureEventData& previous_tap, | |
122 const GestureEventData& current_tap) const { | |
123 if (current_tap.time - previous_tap.time > | |
124 base::TimeDelta::FromMilliseconds( | |
125 ui::GestureConfiguration::max_time_between_double_click_in_ms())) { | |
126 return false; | |
127 } | |
128 | |
129 float double_tap_slop_square = | |
130 GestureConfiguration::max_distance_between_taps_for_double_tap(); | |
131 double_tap_slop_square *= double_tap_slop_square; | |
132 const float delta_x = previous_tap.x - current_tap.x; | |
133 const float delta_y = previous_tap.y - current_tap.y; | |
134 return (delta_x * delta_x + delta_y * delta_y < double_tap_slop_square); | |
135 } | |
136 | |
137 } // namespace content | |
OLD | NEW |