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

Side by Side Diff: content/browser/renderer_host/render_widget_host_input_event_router.cc

Issue 2034213002: Reland: Fix touchpad gesture routing to renderers (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Cleaned up comments Created 4 years, 6 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 2015 The Chromium Authors. All rights reserved. 1 // Copyright 2015 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 "content/browser/renderer_host/render_widget_host_input_event_router.h" 5 #include "content/browser/renderer_host/render_widget_host_input_event_router.h"
6 6
7 #include "base/debug/dump_without_crashing.h" 7 #include "base/debug/dump_without_crashing.h"
8 #include "cc/quads/surface_draw_quad.h" 8 #include "cc/quads/surface_draw_quad.h"
9 #include "cc/surfaces/surface_id_allocator.h" 9 #include "cc/surfaces/surface_id_allocator.h"
10 #include "cc/surfaces/surface_manager.h" 10 #include "cc/surfaces/surface_manager.h"
(...skipping 30 matching lines...) Expand all
41 41
42 if (view == touch_target_) { 42 if (view == touch_target_) {
43 touch_target_ = nullptr; 43 touch_target_ = nullptr;
44 touch_delta_ = gfx::Vector2d(); 44 touch_delta_ = gfx::Vector2d();
45 active_touches_ = 0; 45 active_touches_ = 0;
46 } 46 }
47 47
48 // If the target that's being destroyed is in the gesture target queue, we 48 // If the target that's being destroyed is in the gesture target queue, we
49 // replace it with nullptr so that we maintain the 1:1 correspondence between 49 // replace it with nullptr so that we maintain the 1:1 correspondence between
50 // queue entries and the touch sequences that underly them. 50 // queue entries and the touch sequences that underly them.
51 for (size_t i = 0; i < gesture_target_queue_.size(); ++i) { 51 for (size_t i = 0; i < touchscreen_gesture_target_queue_.size(); ++i) {
52 if (gesture_target_queue_[i].target == view) 52 if (touchscreen_gesture_target_queue_[i].target == view)
53 gesture_target_queue_[i].target = nullptr; 53 touchscreen_gesture_target_queue_[i].target = nullptr;
54 } 54 }
55 55
56 if (view == gesture_target_) { 56 if (view == touchscreen_gesture_target_) {
57 gesture_target_ = nullptr; 57 touchscreen_gesture_target_ = nullptr;
58 gesture_delta_ = gfx::Vector2d(); 58 touchscreen_gesture_delta_ = gfx::Vector2d();
59 }
60
61 if (view == touchpad_gesture_target_) {
62 touchpad_gesture_target_ = nullptr;
63 touchpad_gesture_delta_ = gfx::Vector2d();
59 } 64 }
60 } 65 }
61 66
62 void RenderWidgetHostInputEventRouter::ClearAllObserverRegistrations() { 67 void RenderWidgetHostInputEventRouter::ClearAllObserverRegistrations() {
63 for (auto entry : owner_map_) 68 for (auto entry : owner_map_)
64 entry.second->RemoveObserver(this); 69 entry.second->RemoveObserver(this);
65 owner_map_.clear(); 70 owner_map_.clear();
66 } 71 }
67 72
68 RenderWidgetHostInputEventRouter::HittestDelegate::HittestDelegate( 73 RenderWidgetHostInputEventRouter::HittestDelegate::HittestDelegate(
(...skipping 14 matching lines...) Expand all
83 const cc::SurfaceDrawQuad* surface_quad, 88 const cc::SurfaceDrawQuad* surface_quad,
84 const gfx::Point& point_in_quad_space) { 89 const gfx::Point& point_in_quad_space) {
85 auto it = hittest_data_.find(surface_quad->surface_id); 90 auto it = hittest_data_.find(surface_quad->surface_id);
86 if (it != hittest_data_.end() && !it->second.ignored_for_hittest) 91 if (it != hittest_data_.end() && !it->second.ignored_for_hittest)
87 return true; 92 return true;
88 return false; 93 return false;
89 } 94 }
90 95
91 RenderWidgetHostInputEventRouter::RenderWidgetHostInputEventRouter() 96 RenderWidgetHostInputEventRouter::RenderWidgetHostInputEventRouter()
92 : touch_target_(nullptr), 97 : touch_target_(nullptr),
93 gesture_target_(nullptr), 98 touchscreen_gesture_target_(nullptr),
99 touchpad_gesture_target_(nullptr),
94 active_touches_(0) {} 100 active_touches_(0) {}
95 101
96 RenderWidgetHostInputEventRouter::~RenderWidgetHostInputEventRouter() { 102 RenderWidgetHostInputEventRouter::~RenderWidgetHostInputEventRouter() {
97 // We may be destroyed before some of the owners in the map, so we must 103 // We may be destroyed before some of the owners in the map, so we must
98 // remove ourself from their observer lists. 104 // remove ourself from their observer lists.
99 ClearAllObserverRegistrations(); 105 ClearAllObserverRegistrations();
100 } 106 }
101 107
102 RenderWidgetHostViewBase* RenderWidgetHostInputEventRouter::FindEventTarget( 108 RenderWidgetHostViewBase* RenderWidgetHostInputEventRouter::FindEventTarget(
103 RenderWidgetHostViewBase* root_view, 109 RenderWidgetHostViewBase* root_view,
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after
158 event->x = transformed_point.x(); 164 event->x = transformed_point.x();
159 event->y = transformed_point.y(); 165 event->y = transformed_point.y();
160 166
161 target->ProcessMouseWheelEvent(*event); 167 target->ProcessMouseWheelEvent(*event);
162 } 168 }
163 169
164 void RenderWidgetHostInputEventRouter::RouteGestureEvent( 170 void RenderWidgetHostInputEventRouter::RouteGestureEvent(
165 RenderWidgetHostViewBase* root_view, 171 RenderWidgetHostViewBase* root_view,
166 blink::WebGestureEvent* event, 172 blink::WebGestureEvent* event,
167 const ui::LatencyInfo& latency) { 173 const ui::LatencyInfo& latency) {
168 // We use GestureTapDown to detect the start of a gesture sequence since there 174 switch (event->sourceDevice) {
169 // is no WebGestureEvent equivalent for ET_GESTURE_BEGIN. Note that this 175 case blink::WebGestureDeviceUninitialized:
170 // means the GestureFlingCancel that always comes between ET_GESTURE_BEGIN and 176 NOTREACHED() << "Uninitialized device type is not allowed";
171 // GestureTapDown is sent to the previous target, in case it is still in a 177 break;
172 // fling. 178 case blink::WebGestureDeviceTouchpad:
173 if (event->type == blink::WebInputEvent::GestureTapDown) { 179 RouteTouchpadGestureEvent(root_view, event, latency);
174 if (gesture_target_queue_.empty()) { 180 break;
175 LOG(ERROR) << "Gesture sequence start detected with no target available."; 181 case blink::WebGestureDeviceTouchscreen:
176 // Ignore this gesture sequence as no target is available. 182 RouteTouchscreenGestureEvent(root_view, event, latency);
177 // TODO(wjmaclean): this only happens on Windows, and should not happen. 183 break;
178 // https://crbug.com/595422 184 };
179 gesture_target_ = nullptr;
180 base::debug::DumpWithoutCrashing();
181 return;
182 }
183
184 const GestureTargetData& data = gesture_target_queue_.front();
185 gesture_target_ = data.target;
186 gesture_delta_ = data.delta;
187 gesture_target_queue_.pop_front();
188 }
189
190 if (!gesture_target_)
191 return;
192
193 event->x += gesture_delta_.x();
194 event->y += gesture_delta_.y();
195 gesture_target_->ProcessGestureEvent(*event, latency);
196 } 185 }
197 186
198 void RenderWidgetHostInputEventRouter::RouteTouchEvent( 187 void RenderWidgetHostInputEventRouter::RouteTouchEvent(
199 RenderWidgetHostViewBase* root_view, 188 RenderWidgetHostViewBase* root_view,
200 blink::WebTouchEvent* event, 189 blink::WebTouchEvent* event,
201 const ui::LatencyInfo& latency) { 190 const ui::LatencyInfo& latency) {
202 switch (event->type) { 191 switch (event->type) {
203 case blink::WebInputEvent::TouchStart: { 192 case blink::WebInputEvent::TouchStart: {
204 if (!active_touches_) { 193 if (!active_touches_) {
205 // Since this is the first touch, it defines the target for the rest 194 // Since this is the first touch, it defines the target for the rest
206 // of this sequence. 195 // of this sequence.
207 DCHECK(!touch_target_); 196 DCHECK(!touch_target_);
208 gfx::Point transformed_point; 197 gfx::Point transformed_point;
209 gfx::Point original_point(event->touches[0].position.x, 198 gfx::Point original_point(event->touches[0].position.x,
210 event->touches[0].position.y); 199 event->touches[0].position.y);
211 touch_target_ = 200 touch_target_ =
212 FindEventTarget(root_view, original_point, &transformed_point); 201 FindEventTarget(root_view, original_point, &transformed_point);
213 202
214 // TODO(wjmaclean): Instead of just computing a delta, we should extract 203 // TODO(wjmaclean): Instead of just computing a delta, we should extract
215 // the complete transform. We assume it doesn't change for the duration 204 // the complete transform. We assume it doesn't change for the duration
216 // of the touch sequence, though this could be wrong; a better approach 205 // of the touch sequence, though this could be wrong; a better approach
217 // might be to always transform each point to the touch_target_ 206 // might be to always transform each point to the touch_target_
218 // for the duration of the sequence. 207 // for the duration of the sequence.
219 touch_delta_ = transformed_point - original_point; 208 touch_delta_ = transformed_point - original_point;
220 gesture_target_queue_.emplace_back(touch_target_, touch_delta_); 209 touchscreen_gesture_target_queue_.emplace_back(touch_target_,
210 touch_delta_);
221 211
222 if (!touch_target_) 212 if (!touch_target_)
223 return; 213 return;
224 } 214 }
225 ++active_touches_; 215 ++active_touches_;
226 if (touch_target_) { 216 if (touch_target_) {
227 TransformEventTouchPositions(event, touch_delta_); 217 TransformEventTouchPositions(event, touch_delta_);
228 touch_target_->ProcessTouchEvent(*event, latency); 218 touch_target_->ProcessTouchEvent(*event, latency);
229 } 219 }
230 break; 220 break;
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after
283 void RenderWidgetHostInputEventRouter::OnHittestData( 273 void RenderWidgetHostInputEventRouter::OnHittestData(
284 const FrameHostMsg_HittestData_Params& params) { 274 const FrameHostMsg_HittestData_Params& params) {
285 if (owner_map_.find(params.surface_id.id_namespace()) == owner_map_.end()) { 275 if (owner_map_.find(params.surface_id.id_namespace()) == owner_map_.end()) {
286 return; 276 return;
287 } 277 }
288 HittestData data; 278 HittestData data;
289 data.ignored_for_hittest = params.ignored_for_hittest; 279 data.ignored_for_hittest = params.ignored_for_hittest;
290 hittest_data_[params.surface_id] = data; 280 hittest_data_[params.surface_id] = data;
291 } 281 }
292 282
283 void RenderWidgetHostInputEventRouter::RouteTouchscreenGestureEvent(
284 RenderWidgetHostViewBase* root_view,
285 blink::WebGestureEvent* event,
286 const ui::LatencyInfo& latency) {
287 DCHECK(event->sourceDevice == blink::WebGestureDeviceTouchscreen);
sadrul 2016/06/06 15:21:47 DCHECK_EQ
mohsen 2016/06/06 18:33:41 Done.
288
289 // We use GestureTapDown to detect the start of a gesture sequence since there
290 // is no WebGestureEvent equivalent for ET_GESTURE_BEGIN. Note that this
291 // means the GestureFlingCancel that always comes between ET_GESTURE_BEGIN and
292 // GestureTapDown is sent to the previous target, in case it is still in a
293 // fling.
294 if (event->type == blink::WebInputEvent::GestureTapDown) {
295 if (touchscreen_gesture_target_queue_.empty()) {
296 LOG(ERROR) << "Gesture sequence start detected with no target available.";
297 // Ignore this gesture sequence as no target is available.
298 // TODO(wjmaclean): this only happens on Windows, and should not happen.
299 // https://crbug.com/595422
300 touchscreen_gesture_target_ = nullptr;
301 base::debug::DumpWithoutCrashing();
302 return;
303 }
304
305 const TouchscreenGestureTargetData& data =
306 touchscreen_gesture_target_queue_.front();
307 touchscreen_gesture_target_ = data.target;
308 touchscreen_gesture_delta_ = data.delta;
309 touchscreen_gesture_target_queue_.pop_front();
310 }
311
312 if (!touchscreen_gesture_target_)
313 return;
314
315 event->x += touchscreen_gesture_delta_.x();
316 event->y += touchscreen_gesture_delta_.y();
317 touchscreen_gesture_target_->ProcessGestureEvent(*event, latency);
318 }
319
320 void RenderWidgetHostInputEventRouter::RouteTouchpadGestureEvent(
321 RenderWidgetHostViewBase* root_view,
322 blink::WebGestureEvent* event,
323 const ui::LatencyInfo& latency) {
324 DCHECK(event->sourceDevice == blink::WebGestureDeviceTouchpad);
sadrul 2016/06/06 15:21:47 _EQ
mohsen 2016/06/06 18:33:41 Done.
325 DCHECK(event->type == blink::WebInputEvent::GesturePinchBegin ||
326 event->type == blink::WebInputEvent::GesturePinchUpdate ||
327 event->type == blink::WebInputEvent::GesturePinchEnd);
328
329 if (event->type == blink::WebInputEvent::GesturePinchBegin) {
330 gfx::Point transformed_point;
331 gfx::Point original_point(event->x, event->y);
332 touchpad_gesture_target_ =
333 FindEventTarget(root_view, original_point, &transformed_point);
334 touchpad_gesture_delta_ = transformed_point - original_point;
335 }
336
337 if (!touchpad_gesture_target_)
338 return;
339
340 event->x += touchpad_gesture_delta_.x();
341 event->y += touchpad_gesture_delta_.y();
342 touchpad_gesture_target_->ProcessGestureEvent(*event, latency);
343 }
344
293 } // namespace content 345 } // namespace content
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698