Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1046)

Side by Side Diff: ui/events/gestures/gesture_recognizer_impl.cc

Issue 1907323003: Drag and drop cleans up touch sequences from the source window. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Fix another test. Created 4 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "ui/events/gestures/gesture_recognizer_impl.h" 5 #include "ui/events/gestures/gesture_recognizer_impl.h"
6 6
7 #include <stddef.h> 7 #include <stddef.h>
8 8
9 #include <limits> 9 #include <limits>
10 #include <memory> 10 #include <memory>
(...skipping 111 matching lines...) Expand 10 before | Expand all | Expand 10 after
122 122
123 void GestureRecognizerImpl::CancelActiveTouchesExcept( 123 void GestureRecognizerImpl::CancelActiveTouchesExcept(
124 GestureConsumer* not_cancelled) { 124 GestureConsumer* not_cancelled) {
125 for (const auto& consumer_provider : consumer_gesture_provider_) { 125 for (const auto& consumer_provider : consumer_gesture_provider_) {
126 if (consumer_provider.first == not_cancelled) 126 if (consumer_provider.first == not_cancelled)
127 continue; 127 continue;
128 CancelActiveTouches(consumer_provider.first); 128 CancelActiveTouches(consumer_provider.first);
129 } 129 }
130 } 130 }
131 131
132 void GestureRecognizerImpl::TransferEventsTo(GestureConsumer* current_consumer, 132 void GestureRecognizerImpl::BeginDragAndDrop(GestureConsumer* current_consumer,
133 GestureConsumer* new_consumer) { 133 GestureConsumer* new_consumer) {
134 // This method transfers the gesture stream from |current_consumer| to
135 // |new_consumer|, while ensuring that both retain a touch event stream which
136 // is reasonably valid. In order to do this we
137 // - record what pointers are currently down on |current_consumer|
138 // - cancel touches on consumers other than |current_consumer|
139 // - move the gesture provider from |current_consumer| to |new_consumer|
140 // - synthesize touch presses on |current_consumer|, to get the state of its
141 // new, empty gesture provider in line with the touch state of the consumer
142 // itself
143 // - synthesize touch cancels on |current_consumer|
144 // - retarget the pointers that were previously targeted to
145 // |current_consumer| to |new_consumer|.
146 // NOTE: This currently doesn't synthesize touch press events on
147 // |new_consumer|, so the event stream it sees is still invalid.
148 DCHECK(current_consumer);
149 DCHECK(new_consumer);
150 GestureEventHelper* helper = FindDispatchHelperForConsumer(current_consumer);
151
152 std::vector<int> touchids_targeted_at_current;
153
154 for (const auto& touch_id_target: touch_id_target_) {
155 if (touch_id_target.second == current_consumer)
156 touchids_targeted_at_current.push_back(touch_id_target.first);
157 }
158
159 CancelActiveTouchesExcept(current_consumer);
160
161 std::vector<std::unique_ptr<TouchEvent>> pressing_touches =
162 GetEventPerPointForConsumer(current_consumer, ET_TOUCH_PRESSED);
163 std::vector<std::unique_ptr<TouchEvent>> cancelling_touches =
164 GetEventPerPointForConsumer(current_consumer, ET_TOUCH_CANCELLED);
165
166 TransferConsumer(current_consumer, new_consumer, &consumer_gesture_provider_);
167
168 if (!helper)
169 return;
170
171 // We're now in a situation where current_consumer has no gesture recognizer,
172 // but has some pointers down which need cancelling. In order to ensure that
173 // the GR sees a valid event stream, synthesize a touch press per pointer, and
174 // then synthesize a touch cancel per pointer. These extra touch presses will
175 // be filtered out in the RenderWidgetHostViewAura.
176
177 for (std::unique_ptr<TouchEvent>& event : pressing_touches)
178 helper->DispatchSyntheticTouchEvent(event.get());
sadrul 2016/05/03 18:38:16 We really shouldn't dispatch a second set of touch
tdresser 2016/05/03 18:56:42 That would mean we'd need to relax this: https://c
sadrul 2016/05/04 13:28:18 If not overly complicated, then yeah, I would go w
179
180 for (std::unique_ptr<TouchEvent>& event : cancelling_touches)
181 helper->DispatchSyntheticTouchEvent(event.get());
182
183 for (int touch_id : touchids_targeted_at_current)
184 touch_id_target_[touch_id] = new_consumer;
185 }
186
187
188 void GestureRecognizerImpl::BeginTabDrag(GestureConsumer* current_consumer,
189 GestureConsumer* new_consumer) {
190 // Tab Drag requires that the touches on |current_consumer| not be
191 // cancelled. We transfer the gesture provider from |current_consumer| to
192 // |new_consumer| without bothering to make the event stream valid for either
193 // consumer.
134 DCHECK(current_consumer); 194 DCHECK(current_consumer);
135 DCHECK(new_consumer); 195 DCHECK(new_consumer);
136 196
137 CancelActiveTouchesExcept(current_consumer); 197 CancelActiveTouchesExcept(current_consumer);
138 198
139 TransferTouchIdToConsumerMap(current_consumer, new_consumer, 199 TransferTouchIdToConsumerMap(current_consumer, new_consumer,
140 &touch_id_target_); 200 &touch_id_target_);
141 TransferConsumer(current_consumer, new_consumer, &consumer_gesture_provider_); 201 TransferConsumer(current_consumer, new_consumer, &consumer_gesture_provider_);
142 } 202 }
143 203
144 bool GestureRecognizerImpl::GetLastTouchPointForTarget( 204 bool GestureRecognizerImpl::GetLastTouchPointForTarget(
145 GestureConsumer* consumer, 205 GestureConsumer* consumer,
146 gfx::PointF* point) { 206 gfx::PointF* point) {
147 if (consumer_gesture_provider_.count(consumer) == 0) 207 if (consumer_gesture_provider_.count(consumer) == 0)
148 return false; 208 return false;
149 const MotionEvent& pointer_state = 209 const MotionEvent& pointer_state =
150 consumer_gesture_provider_[consumer]->pointer_state(); 210 consumer_gesture_provider_[consumer]->pointer_state();
151 if (!pointer_state.GetPointerCount()) 211 if (!pointer_state.GetPointerCount())
152 return false; 212 return false;
153 *point = gfx::PointF(pointer_state.GetX(), pointer_state.GetY()); 213 *point = gfx::PointF(pointer_state.GetX(), pointer_state.GetY());
154 return true; 214 return true;
155 } 215 }
156 216
157 bool GestureRecognizerImpl::CancelActiveTouches(GestureConsumer* consumer) { 217 std::vector<std::unique_ptr<TouchEvent>>
158 bool cancelled_touch = false; 218 GestureRecognizerImpl::GetEventPerPointForConsumer(GestureConsumer* consumer,
219 EventType type) {
220 std::vector<std::unique_ptr<TouchEvent>> cancelling_touches;
159 if (consumer_gesture_provider_.count(consumer) == 0) 221 if (consumer_gesture_provider_.count(consumer) == 0)
160 return false; 222 return cancelling_touches;
161 const MotionEventAura& pointer_state = 223 const MotionEventAura& pointer_state =
162 consumer_gesture_provider_[consumer]->pointer_state(); 224 consumer_gesture_provider_[consumer]->pointer_state();
163 if (pointer_state.GetPointerCount() == 0) 225 if (pointer_state.GetPointerCount() == 0)
226 return cancelling_touches;
227 for (size_t i = 0; i < pointer_state.GetPointerCount(); ++i) {
228 std::unique_ptr<TouchEvent> touch_event(new TouchEvent(
229 type, gfx::Point(), EF_IS_SYNTHESIZED, pointer_state.GetPointerId(i),
230 EventTimeForNow(), 0.0f, 0.0f, 0.0f, 0.0f));
231 gfx::PointF point(pointer_state.GetX(i), pointer_state.GetY(i));
232 touch_event->set_location_f(point);
233 touch_event->set_root_location_f(point);
234 cancelling_touches.push_back(std::move(touch_event));
235 }
236 return cancelling_touches;
237 }
238
239 bool GestureRecognizerImpl::CancelActiveTouches(GestureConsumer* consumer) {
240 GestureEventHelper* helper =
241 FindDispatchHelperForConsumer(consumer);
242
243 if (!helper)
164 return false; 244 return false;
165 // pointer_state is modified every time after DispatchCancelTouchEvent. 245
166 std::unique_ptr<MotionEvent> pointer_state_clone = pointer_state.Clone(); 246 std::vector<std::unique_ptr<TouchEvent>> cancelling_touches =
167 for (size_t i = 0; i < pointer_state_clone->GetPointerCount(); ++i) { 247 GetEventPerPointForConsumer(consumer, ET_TOUCH_CANCELLED);
168 TouchEvent touch_event(ui::ET_TOUCH_CANCELLED, gfx::Point(), 248 for (const std::unique_ptr<TouchEvent>& cancelling_touch : cancelling_touches)
169 ui::EF_IS_SYNTHESIZED, 249 helper->DispatchSyntheticTouchEvent(cancelling_touch.get());
170 pointer_state_clone->GetPointerId(i), 250 return cancelling_touches.size() > 0U;
171 ui::EventTimeForNow(), 0.0f, 0.0f, 0.0f, 0.0f);
172 gfx::PointF point(pointer_state_clone->GetX(i),
173 pointer_state_clone->GetY(i));
174 touch_event.set_location_f(point);
175 touch_event.set_root_location_f(point);
176 GestureEventHelper* helper = FindDispatchHelperForConsumer(consumer);
177 if (helper)
178 helper->DispatchCancelTouchEvent(consumer, &touch_event);
179 cancelled_touch = true;
180 }
181 return cancelled_touch;
182 } 251 }
183 252
184 //////////////////////////////////////////////////////////////////////////////// 253 ////////////////////////////////////////////////////////////////////////////////
185 // GestureRecognizerImpl, private: 254 // GestureRecognizerImpl, private:
186 255
187 GestureProviderAura* GestureRecognizerImpl::GetGestureProviderForConsumer( 256 GestureProviderAura* GestureRecognizerImpl::GetGestureProviderForConsumer(
188 GestureConsumer* consumer) { 257 GestureConsumer* consumer) {
189 GestureProviderAura* gesture_provider = consumer_gesture_provider_[consumer]; 258 GestureProviderAura* gesture_provider = consumer_gesture_provider_[consumer];
190 if (!gesture_provider) { 259 if (!gesture_provider) {
191 gesture_provider = CreateGestureProvider(consumer, this); 260 gesture_provider = CreateGestureProvider(consumer, this);
(...skipping 114 matching lines...) Expand 10 before | Expand all | Expand 10 after
306 std::vector<GestureEventHelper*>::iterator it; 375 std::vector<GestureEventHelper*>::iterator it;
307 for (it = helpers.begin(); it != helpers.end(); ++it) 376 for (it = helpers.begin(); it != helpers.end(); ++it)
308 gesture_recognizer->AddGestureEventHelper(*it); 377 gesture_recognizer->AddGestureEventHelper(*it);
309 378
310 helpers.clear(); 379 helpers.clear();
311 g_gesture_recognizer_instance = 380 g_gesture_recognizer_instance =
312 static_cast<GestureRecognizerImpl*>(gesture_recognizer); 381 static_cast<GestureRecognizerImpl*>(gesture_recognizer);
313 } 382 }
314 383
315 } // namespace ui 384 } // namespace ui
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698