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

Unified Diff: content/browser/renderer_host/input/input_router_impl.cc

Issue 250923004: Synthesize ctrl-wheel events on touchpad pinch (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 6 years, 8 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « content/browser/renderer_host/input/input_router_impl.h ('k') | no next file » | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: content/browser/renderer_host/input/input_router_impl.cc
diff --git a/content/browser/renderer_host/input/input_router_impl.cc b/content/browser/renderer_host/input/input_router_impl.cc
index 129f34698a3b97b521c3dbc4f61b1194154da54f..ee49300a57a3ffa3616c2dd31dff3b22de13c3ab 100644
--- a/content/browser/renderer_host/input/input_router_impl.cc
+++ b/content/browser/renderer_host/input/input_router_impl.cc
@@ -143,6 +143,8 @@ InputRouterImpl::InputRouterImpl(IPC::Sender* sender,
move_caret_pending_(false),
mouse_move_pending_(false),
mouse_wheel_pending_(false),
+ pending_touchpad_pinch_(false),
+ current_wheel_event_is_for_pinch_(false),
touch_ack_timeout_supported_(false),
current_view_flags_(0),
current_ack_source_(ACK_SOURCE_NONE),
@@ -206,11 +208,25 @@ void InputRouterImpl::SendMouseEvent(
void InputRouterImpl::SendWheelEvent(
const MouseWheelEventWithLatencyInfo& wheel_event) {
- // If there's already a mouse wheel event waiting to be sent to the renderer,
- // add the new deltas to that event. Not doing so (e.g., by dropping the old
- // event, as for mouse moves) results in very slow scrolling on the Mac (on
- // which many, very small wheel events are sent).
if (mouse_wheel_pending_) {
+ // If the provided event is for touchpad pinch, we don't want to coalesce
+ // it in with other wheel events as that would make the ACK handling
jdduke (slow) 2014/05/01 15:44:47 I'm starting to think maintaining separate Touchpa
jdduke (slow) 2014/05/01 16:26:01 This is very much a future thing :)
Rick Byers 2014/05/01 17:34:57 Agreed. The gesture streams are as distinct as mo
+ // difficult and could require coalescing correspending GesturePinchUpdate
+ // events in the GestureEventQueue. Do nothing for now, we'll send
+ // wheel_event_for_pending_pinch_ when the ACK for this wheel event
+ // arrives.
+ if (pending_touchpad_pinch_) {
+ DCHECK(!current_wheel_event_is_for_pinch_);
+ DCHECK(wheel_event.latency.trace_id ==
+ wheel_event_for_pending_pinch_.latency.trace_id);
+ return;
+ }
+
+ // If there's already a mouse wheel event waiting to be sent to the
+ // renderer,
+ // add the new deltas to that event. Not doing so (e.g., by dropping the old
+ // event, as for mouse moves) results in very slow scrolling on the Mac (on
+ // which many, very small wheel events are sent).
if (coalesced_mouse_wheel_events_.empty() ||
!coalesced_mouse_wheel_events_.back().CanCoalesceWith(wheel_event)) {
coalesced_mouse_wheel_events_.push_back(wheel_event);
@@ -219,6 +235,7 @@ void InputRouterImpl::SendWheelEvent(
}
return;
}
+
mouse_wheel_pending_ = true;
current_wheel_event_ = wheel_event;
@@ -426,16 +443,13 @@ void InputRouterImpl::FilterAndSendWebInputEvent(
void InputRouterImpl::OfferToHandlers(const WebInputEvent& input_event,
const ui::LatencyInfo& latency_info,
bool is_keyboard_shortcut) {
- // Trackpad pinch gestures are not yet handled by the renderer.
- // TODO(rbyers): Send mousewheel for trackpad pinch - crbug.com/289887.
- if (input_event.type == WebInputEvent::GesturePinchUpdate &&
- static_cast<const WebGestureEvent&>(input_event).sourceDevice ==
- WebGestureEvent::Touchpad) {
- ProcessInputEventAck(input_event.type,
- INPUT_EVENT_ACK_STATE_NOT_CONSUMED,
- latency_info,
- ACK_SOURCE_NONE);
- return;
+ if (input_event.type == WebInputEvent::GesturePinchUpdate) {
jdduke (slow) 2014/05/01 15:44:47 Can you explain to me why it's important for the v
jdduke (slow) 2014/05/01 16:26:01 As per offline discussion, nevermind this comment.
+ const WebGestureEvent& pinch_event =
+ static_cast<const WebGestureEvent&>(input_event);
+ if (pinch_event.sourceDevice == WebGestureEvent::Touchpad) {
+ SendSyntheticWheelEventForPinch(pinch_event, latency_info);
+ return;
+ }
}
if (OfferToOverscrollController(input_event, latency_info))
@@ -533,6 +547,27 @@ bool InputRouterImpl::OfferToRenderer(const WebInputEvent& input_event,
return false;
}
+void InputRouterImpl::SendSyntheticWheelEventForPinch(
+ const blink::WebGestureEvent& pinch_event,
+ const ui::LatencyInfo& latency_info) {
+ // We match IE and Firefox behavior on Windows by sending fake wheel events
+ // with the ctrl modifier set when we see trackpad pinch gestures. Ideally
+ // we'd someday get a standard 'pinch' event and send that instead.
+ DCHECK(!pending_touchpad_pinch_);
+ DCHECK(!current_wheel_event_is_for_pinch_);
+ WebMouseWheelEvent wheelEvent;
+ wheelEvent.type = WebInputEvent::MouseWheel;
+ wheelEvent.timeStampSeconds = pinch_event.timeStampSeconds;
+ wheelEvent.modifiers = pinch_event.modifiers | WebInputEvent::ControlKey;
+ wheelEvent.deltaX = 0;
+ wheelEvent.deltaY = pinch_event.data.pinchUpdate.scale - 1;
+ wheelEvent.hasPreciseScrollingDeltas = true;
+ wheelEvent.wheelTicksX = 0;
+ wheelEvent.wheelTicksY = pinch_event.data.pinchUpdate.scale > 0 ? 1 : -1;
+
+ SendWheelEvent(MouseWheelEventWithLatencyInfo(wheelEvent, latency_info));
+}
+
void InputRouterImpl::OnInputEventAck(WebInputEvent::Type event_type,
InputEventAckState ack_result,
const ui::LatencyInfo& latency_info) {
@@ -670,18 +705,38 @@ void InputRouterImpl::ProcessMouseAck(blink::WebInputEvent::Type type,
void InputRouterImpl::ProcessWheelAck(InputEventAckState ack_result,
const ui::LatencyInfo& latency) {
+ DCHECK(mouse_wheel_pending_);
ProcessAckForOverscroll(current_wheel_event_.event, ack_result);
// TODO(miletus): Add renderer side latency to each uncoalesced mouse
// wheel event and add terminal component to each of them.
current_wheel_event_.latency.AddNewLatencyFrom(latency);
- // Process the unhandled wheel event here before calling SendWheelEvent()
- // since it will mutate current_wheel_event_.
- ack_handler_->OnWheelEventAck(current_wheel_event_, ack_result);
+
+ if (current_wheel_event_is_for_pinch_) {
+ DCHECK(pending_touchpad_pinch_);
+ DCHECK(current_wheel_event_.latency.trace_id ==
+ wheel_event_for_pending_pinch_.latency.trace_id);
+
+ // Ack the GesturePinchUpdate event that generated this wheel event.
+ ProcessInputEventAck(WebInputEvent::GesturePinchUpdate,
+ ack_result,
+ current_wheel_event_.latency,
+ ACK_SOURCE_NONE);
+ current_wheel_event_is_for_pinch_ = false;
+ pending_touchpad_pinch_ = false;
+ } else {
+ // Process the unhandled wheel event here before calling SendWheelEvent()
+ // since it will mutate current_wheel_event_.
+ ack_handler_->OnWheelEventAck(current_wheel_event_, ack_result);
+ }
mouse_wheel_pending_ = false;
- // Now send the next (coalesced) mouse wheel event.
- if (!coalesced_mouse_wheel_events_.empty()) {
+ // Send the next (coalesced or synthetic) mouse wheel event.
+ if (pending_touchpad_pinch_) {
+ DCHECK(!current_wheel_event_is_for_pinch_);
+ current_wheel_event_is_for_pinch_ = true;
+ SendWheelEvent(wheel_event_for_pending_pinch_);
+ } else if (!coalesced_mouse_wheel_events_.empty()) {
MouseWheelEventWithLatencyInfo next_wheel_event =
coalesced_mouse_wheel_events_.front();
coalesced_mouse_wheel_events_.pop_front();
« no previous file with comments | « content/browser/renderer_host/input/input_router_impl.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698