| OLD | NEW |
| 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/renderer/input/render_widget_input_handler.h" | 5 #include "content/renderer/input/render_widget_input_handler.h" |
| 6 | 6 |
| 7 #include <stddef.h> | 7 #include <stddef.h> |
| 8 #include <stdint.h> | 8 #include <stdint.h> |
| 9 #include <utility> | 9 #include <utility> |
| 10 | 10 |
| (...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 124 event.type, latency_info.timestamps_of_coalesced_events()[i], now); | 124 event.type, latency_info.timestamps_of_coalesced_events()[i], now); |
| 125 } | 125 } |
| 126 } | 126 } |
| 127 | 127 |
| 128 void LogPassiveLatency(int64_t latency) { | 128 void LogPassiveLatency(int64_t latency) { |
| 129 UMA_HISTOGRAM_CUSTOM_COUNTS("Event.PassiveListeners.Latency", latency, 1, | 129 UMA_HISTOGRAM_CUSTOM_COUNTS("Event.PassiveListeners.Latency", latency, 1, |
| 130 10000000, 100); | 130 10000000, 100); |
| 131 } | 131 } |
| 132 | 132 |
| 133 void LogPassiveEventListenersUma(WebInputEventResult result, | 133 void LogPassiveEventListenersUma(WebInputEventResult result, |
| 134 bool passive, | 134 bool non_blocking, |
| 135 bool cancelable, | 135 bool cancelable, |
| 136 double event_timestamp, | 136 double event_timestamp, |
| 137 const ui::LatencyInfo& latency_info) { | 137 const ui::LatencyInfo& latency_info) { |
| 138 enum { | 138 enum { |
| 139 PASSIVE_LISTENER_UMA_ENUM_PASSIVE, | 139 PASSIVE_LISTENER_UMA_ENUM_PASSIVE, |
| 140 PASSIVE_LISTENER_UMA_ENUM_UNCANCELABLE, | 140 PASSIVE_LISTENER_UMA_ENUM_UNCANCELABLE, |
| 141 PASSIVE_LISTENER_UMA_ENUM_SUPPRESSED, | 141 PASSIVE_LISTENER_UMA_ENUM_SUPPRESSED, |
| 142 PASSIVE_LISTENER_UMA_ENUM_CANCELABLE, | 142 PASSIVE_LISTENER_UMA_ENUM_CANCELABLE, |
| 143 PASSIVE_LISTENER_UMA_ENUM_CANCELABLE_AND_CANCELED, | 143 PASSIVE_LISTENER_UMA_ENUM_CANCELABLE_AND_CANCELED, |
| 144 PASSIVE_LISTENER_UMA_ENUM_COUNT | 144 PASSIVE_LISTENER_UMA_ENUM_COUNT |
| 145 }; | 145 }; |
| 146 | 146 |
| 147 int enum_value; | 147 int enum_value; |
| 148 if (passive) | 148 if (non_blocking) |
| 149 enum_value = PASSIVE_LISTENER_UMA_ENUM_PASSIVE; | 149 enum_value = PASSIVE_LISTENER_UMA_ENUM_PASSIVE; |
| 150 else if (!cancelable) | 150 else if (!cancelable) |
| 151 enum_value = PASSIVE_LISTENER_UMA_ENUM_UNCANCELABLE; | 151 enum_value = PASSIVE_LISTENER_UMA_ENUM_UNCANCELABLE; |
| 152 else if (result == WebInputEventResult::HandledApplication) | 152 else if (result == WebInputEventResult::HandledApplication) |
| 153 enum_value = PASSIVE_LISTENER_UMA_ENUM_CANCELABLE_AND_CANCELED; | 153 enum_value = PASSIVE_LISTENER_UMA_ENUM_CANCELABLE_AND_CANCELED; |
| 154 else if (result == WebInputEventResult::HandledSuppressed) | 154 else if (result == WebInputEventResult::HandledSuppressed) |
| 155 enum_value = PASSIVE_LISTENER_UMA_ENUM_SUPPRESSED; | 155 enum_value = PASSIVE_LISTENER_UMA_ENUM_SUPPRESSED; |
| 156 else | 156 else |
| 157 enum_value = PASSIVE_LISTENER_UMA_ENUM_CANCELABLE; | 157 enum_value = PASSIVE_LISTENER_UMA_ENUM_CANCELABLE; |
| 158 | 158 |
| (...skipping 25 matching lines...) Expand all Loading... |
| 184 ignore_ack_for_mouse_move_from_debugger_(false) { | 184 ignore_ack_for_mouse_move_from_debugger_(false) { |
| 185 DCHECK(delegate); | 185 DCHECK(delegate); |
| 186 DCHECK(widget); | 186 DCHECK(widget); |
| 187 delegate->SetInputHandler(this); | 187 delegate->SetInputHandler(this); |
| 188 } | 188 } |
| 189 | 189 |
| 190 RenderWidgetInputHandler::~RenderWidgetInputHandler() {} | 190 RenderWidgetInputHandler::~RenderWidgetInputHandler() {} |
| 191 | 191 |
| 192 void RenderWidgetInputHandler::HandleInputEvent( | 192 void RenderWidgetInputHandler::HandleInputEvent( |
| 193 const WebInputEvent& input_event, | 193 const WebInputEvent& input_event, |
| 194 const ui::LatencyInfo& latency_info) { | 194 const ui::LatencyInfo& latency_info, |
| 195 // TODO(dtapuska): Passive support not implemented yet crbug.com/489802 | 195 InputEventDispatchType dispatch_type) { |
| 196 bool passive = false; | |
| 197 base::AutoReset<bool> handling_input_event_resetter(&handling_input_event_, | 196 base::AutoReset<bool> handling_input_event_resetter(&handling_input_event_, |
| 198 true); | 197 true); |
| 199 base::AutoReset<WebInputEvent::Type> handling_event_type_resetter( | 198 base::AutoReset<WebInputEvent::Type> handling_event_type_resetter( |
| 200 &handling_event_type_, input_event.type); | 199 &handling_event_type_, input_event.type); |
| 201 | 200 |
| 202 // Calls into |didOverscroll()| while handling this event will populate | 201 // Calls into |didOverscroll()| while handling this event will populate |
| 203 // |event_overscroll|, which in turn will be bundled with the event ack. | 202 // |event_overscroll|, which in turn will be bundled with the event ack. |
| 204 scoped_ptr<DidOverscrollParams> event_overscroll; | 203 scoped_ptr<DidOverscrollParams> event_overscroll; |
| 205 base::AutoReset<scoped_ptr<DidOverscrollParams>*> | 204 base::AutoReset<scoped_ptr<DidOverscrollParams>*> |
| 206 handling_event_overscroll_resetter(&handling_event_overscroll_, | 205 handling_event_overscroll_resetter(&handling_event_overscroll_, |
| (...skipping 100 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 307 | 306 |
| 308 WebInputEventResult processed = prevent_default | 307 WebInputEventResult processed = prevent_default |
| 309 ? WebInputEventResult::HandledSuppressed | 308 ? WebInputEventResult::HandledSuppressed |
| 310 : WebInputEventResult::NotHandled; | 309 : WebInputEventResult::NotHandled; |
| 311 if (input_event.type != WebInputEvent::Char || !suppress_next_char_events_) { | 310 if (input_event.type != WebInputEvent::Char || !suppress_next_char_events_) { |
| 312 suppress_next_char_events_ = false; | 311 suppress_next_char_events_ = false; |
| 313 if (processed == WebInputEventResult::NotHandled && widget_->webwidget()) | 312 if (processed == WebInputEventResult::NotHandled && widget_->webwidget()) |
| 314 processed = widget_->webwidget()->handleInputEvent(input_event); | 313 processed = widget_->webwidget()->handleInputEvent(input_event); |
| 315 } | 314 } |
| 316 | 315 |
| 316 bool non_blocking = |
| 317 dispatch_type == InputEventDispatchType::DISPATCH_TYPE_NON_BLOCKING; |
| 317 // TODO(dtapuska): Use the input_event.timeStampSeconds as the start | 318 // TODO(dtapuska): Use the input_event.timeStampSeconds as the start |
| 318 // ideally this should be when the event was sent by the compositor to the | 319 // ideally this should be when the event was sent by the compositor to the |
| 319 // renderer. crbug.com/565348 | 320 // renderer. crbug.com/565348 |
| 320 if (input_event.type == WebInputEvent::TouchStart || | 321 if (input_event.type == WebInputEvent::TouchStart || |
| 321 input_event.type == WebInputEvent::TouchMove || | 322 input_event.type == WebInputEvent::TouchMove || |
| 322 input_event.type == WebInputEvent::TouchEnd) { | 323 input_event.type == WebInputEvent::TouchEnd) { |
| 323 LogPassiveEventListenersUma( | 324 LogPassiveEventListenersUma( |
| 324 processed, passive, | 325 processed, non_blocking, |
| 325 static_cast<const WebTouchEvent&>(input_event).cancelable, | 326 static_cast<const WebTouchEvent&>(input_event).cancelable, |
| 326 input_event.timeStampSeconds, latency_info); | 327 input_event.timeStampSeconds, latency_info); |
| 327 } else if (input_event.type == WebInputEvent::MouseWheel) { | 328 } else if (input_event.type == WebInputEvent::MouseWheel) { |
| 328 LogPassiveEventListenersUma(processed, passive, !passive, | 329 LogPassiveEventListenersUma(processed, non_blocking, !non_blocking, |
| 329 input_event.timeStampSeconds, latency_info); | 330 input_event.timeStampSeconds, latency_info); |
| 330 } | 331 } |
| 331 | 332 |
| 332 // If this RawKeyDown event corresponds to a browser keyboard shortcut and | 333 // If this RawKeyDown event corresponds to a browser keyboard shortcut and |
| 333 // it's not processed by webkit, then we need to suppress the upcoming Char | 334 // it's not processed by webkit, then we need to suppress the upcoming Char |
| 334 // events. | 335 // events. |
| 335 bool is_keyboard_shortcut = | 336 bool is_keyboard_shortcut = |
| 336 input_event.type == WebInputEvent::RawKeyDown && | 337 input_event.type == WebInputEvent::RawKeyDown && |
| 337 static_cast<const WebKeyboardEvent&>(input_event).isBrowserShortcut; | 338 static_cast<const WebKeyboardEvent&>(input_event).isBrowserShortcut; |
| 338 if (processed == WebInputEventResult::NotHandled && is_keyboard_shortcut) | 339 if (processed == WebInputEventResult::NotHandled && is_keyboard_shortcut) |
| (...skipping 16 matching lines...) Expand all Loading... |
| 355 gfx::ToFlooredPoint(touch_event.touches[i].position))) { | 356 gfx::ToFlooredPoint(touch_event.touches[i].position))) { |
| 356 ack_result = INPUT_EVENT_ACK_STATE_NOT_CONSUMED; | 357 ack_result = INPUT_EVENT_ACK_STATE_NOT_CONSUMED; |
| 357 break; | 358 break; |
| 358 } | 359 } |
| 359 } | 360 } |
| 360 } | 361 } |
| 361 | 362 |
| 362 // Send mouse wheel events and their disposition to the compositor thread, so | 363 // Send mouse wheel events and their disposition to the compositor thread, so |
| 363 // that they can be used to produce the elastic overscroll effect on Mac. | 364 // that they can be used to produce the elastic overscroll effect on Mac. |
| 364 if (input_event.type == WebInputEvent::MouseWheel) { | 365 if (input_event.type == WebInputEvent::MouseWheel) { |
| 365 delegate_->ObserveWheelEventAndResult( | 366 const WebMouseWheelEvent& wheel_event = |
| 366 static_cast<const WebMouseWheelEvent&>(input_event), | 367 static_cast<const WebMouseWheelEvent&>(input_event); |
| 367 event_overscroll ? event_overscroll->latest_overscroll_delta | 368 if (wheel_event.canScroll) { |
| 368 : gfx::Vector2dF(), | 369 delegate_->ObserveWheelEventAndResult( |
| 369 processed != WebInputEventResult::NotHandled); | 370 wheel_event, |
| 371 event_overscroll ? event_overscroll->latest_overscroll_delta |
| 372 : gfx::Vector2dF(), |
| 373 processed != WebInputEventResult::NotHandled); |
| 374 } |
| 370 } | 375 } |
| 371 | 376 |
| 372 bool frame_pending = | 377 bool frame_pending = |
| 373 widget_->compositor() && widget_->compositor()->BeginMainFrameRequested(); | 378 widget_->compositor() && widget_->compositor()->BeginMainFrameRequested(); |
| 374 | 379 |
| 375 // If we don't have a fast and accurate Now(), we assume the input handlers | 380 // If we don't have a fast and accurate Now(), we assume the input handlers |
| 376 // are heavy and rate limit them. | 381 // are heavy and rate limit them. |
| 377 bool rate_limiting_wanted = input_event.type == WebInputEvent::MouseMove || | 382 bool rate_limiting_wanted = input_event.type == WebInputEvent::MouseMove || |
| 378 input_event.type == WebInputEvent::MouseWheel; | 383 input_event.type == WebInputEvent::MouseWheel; |
| 379 if (rate_limiting_wanted && !start_time.is_null()) { | 384 if (rate_limiting_wanted && !start_time.is_null()) { |
| 380 base::TimeTicks end_time = base::TimeTicks::Now(); | 385 base::TimeTicks end_time = base::TimeTicks::Now(); |
| 381 total_input_handling_time_this_frame_ += (end_time - start_time); | 386 total_input_handling_time_this_frame_ += (end_time - start_time); |
| 382 rate_limiting_wanted = | 387 rate_limiting_wanted = |
| 383 total_input_handling_time_this_frame_.InMicroseconds() > | 388 total_input_handling_time_this_frame_.InMicroseconds() > |
| 384 kInputHandlingTimeThrottlingThresholdMicroseconds; | 389 kInputHandlingTimeThrottlingThresholdMicroseconds; |
| 385 } | 390 } |
| 386 | 391 |
| 387 TRACE_EVENT_SYNTHETIC_DELAY_END("blink.HandleInputEvent"); | 392 TRACE_EVENT_SYNTHETIC_DELAY_END("blink.HandleInputEvent"); |
| 388 | 393 |
| 389 // Note that we can't use handling_event_type_ here since it will be overriden | 394 // Note that we can't use handling_event_type_ here since it will be overriden |
| 390 // by reentrant calls for events after the paused one. | 395 // by reentrant calls for events after the paused one. |
| 391 bool no_ack = ignore_ack_for_mouse_move_from_debugger_ && | 396 bool no_ack = ignore_ack_for_mouse_move_from_debugger_ && |
| 392 input_event.type == WebInputEvent::MouseMove; | 397 input_event.type == WebInputEvent::MouseMove; |
| 393 if (WebInputEventTraits::WillReceiveAckFromRenderer(input_event) && !no_ack) { | 398 if (non_blocking) { |
| 399 // |non_blocking| means it was ack'd already by the InputHandlerProxy |
| 400 // so let the delegate know the event has been handled. |
| 401 delegate_->NonBlockingInputEventHandled(input_event.type); |
| 402 } else if (WebInputEventTraits::WillReceiveAckFromRenderer(input_event) && |
| 403 !no_ack) { |
| 394 scoped_ptr<InputEventAck> response(new InputEventAck( | 404 scoped_ptr<InputEventAck> response(new InputEventAck( |
| 395 input_event.type, ack_result, swap_latency_info, | 405 input_event.type, ack_result, swap_latency_info, |
| 396 std::move(event_overscroll), | 406 std::move(event_overscroll), |
| 397 WebInputEventTraits::GetUniqueTouchEventId(input_event))); | 407 WebInputEventTraits::GetUniqueTouchEventId(input_event))); |
| 398 if (rate_limiting_wanted && frame_pending && !widget_->is_hidden()) { | 408 if (rate_limiting_wanted && frame_pending && !widget_->is_hidden()) { |
| 399 // We want to rate limit the input events in this case, so we'll wait for | 409 // We want to rate limit the input events in this case, so we'll wait for |
| 400 // painting to finish before ACKing this message. | 410 // painting to finish before ACKing this message. |
| 401 TRACE_EVENT_INSTANT0( | 411 TRACE_EVENT_INSTANT0( |
| 402 "renderer", | 412 "renderer", |
| 403 "RenderWidgetInputHandler::OnHandleInputEvent ack throttled", | 413 "RenderWidgetInputHandler::OnHandleInputEvent ack throttled", |
| (...skipping 108 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 512 if (pending_input_event_ack_) { | 522 if (pending_input_event_ack_) { |
| 513 TRACE_EVENT_ASYNC_END0("input", | 523 TRACE_EVENT_ASYNC_END0("input", |
| 514 "RenderWidgetInputHandler::ThrottledInputEventAck", | 524 "RenderWidgetInputHandler::ThrottledInputEventAck", |
| 515 pending_input_event_ack_.get()); | 525 pending_input_event_ack_.get()); |
| 516 delegate_->OnInputEventAck(std::move(pending_input_event_ack_)); | 526 delegate_->OnInputEventAck(std::move(pending_input_event_ack_)); |
| 517 } | 527 } |
| 518 total_input_handling_time_this_frame_ = base::TimeDelta(); | 528 total_input_handling_time_this_frame_ = base::TimeDelta(); |
| 519 } | 529 } |
| 520 | 530 |
| 521 } // namespace content | 531 } // namespace content |
| OLD | NEW |