| OLD | NEW |
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 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 "core/input/PointerEventManager.h" | 5 #include "core/input/PointerEventManager.h" |
| 6 | 6 |
| 7 #include "core/dom/DocumentUserGestureToken.h" | 7 #include "core/dom/DocumentUserGestureToken.h" |
| 8 #include "core/dom/ElementTraversal.h" | 8 #include "core/dom/ElementTraversal.h" |
| 9 #include "core/dom/shadow/FlatTreeTraversal.h" | 9 #include "core/dom/shadow/FlatTreeTraversal.h" |
| 10 #include "core/events/MouseEvent.h" | 10 #include "core/events/MouseEvent.h" |
| (...skipping 151 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 162 } | 162 } |
| 163 | 163 |
| 164 if (!RuntimeEnabledFeatures::pointerEventEnabled()) | 164 if (!RuntimeEnabledFeatures::pointerEventEnabled()) |
| 165 return WebInputEventResult::NotHandled; | 165 return WebInputEventResult::NotHandled; |
| 166 if (!checkForListener || target->hasEventListeners(eventType)) { | 166 if (!checkForListener || target->hasEventListeners(eventType)) { |
| 167 UseCounter::count(m_frame->document(), UseCounter::PointerEventDispatch); | 167 UseCounter::count(m_frame->document(), UseCounter::PointerEventDispatch); |
| 168 if (eventType == EventTypeNames::pointerdown) | 168 if (eventType == EventTypeNames::pointerdown) |
| 169 UseCounter::count(m_frame->document(), | 169 UseCounter::count(m_frame->document(), |
| 170 UseCounter::PointerEventDispatchPointerDown); | 170 UseCounter::PointerEventDispatchPointerDown); |
| 171 | 171 |
| 172 std::unique_ptr<UserGestureIndicator> gestureIndicator; | |
| 173 if (eventType == EventTypeNames::pointerup && | |
| 174 pointerEvent->pointerType() == "touch") { | |
| 175 gestureIndicator = | |
| 176 wrapUnique(new UserGestureIndicator(DocumentUserGestureToken::create( | |
| 177 target->toNode() ? &target->toNode()->document() : nullptr))); | |
| 178 } | |
| 179 | |
| 180 DispatchEventResult dispatchResult = target->dispatchEvent(pointerEvent); | 172 DispatchEventResult dispatchResult = target->dispatchEvent(pointerEvent); |
| 181 return EventHandlingUtil::toWebInputEventResult(dispatchResult); | 173 return EventHandlingUtil::toWebInputEventResult(dispatchResult); |
| 182 } | 174 } |
| 183 return WebInputEventResult::NotHandled; | 175 return WebInputEventResult::NotHandled; |
| 184 } | 176 } |
| 185 | 177 |
| 186 EventTarget* PointerEventManager::getEffectiveTargetForPointerEvent( | 178 EventTarget* PointerEventManager::getEffectiveTargetForPointerEvent( |
| 187 EventTarget* target, | 179 EventTarget* target, |
| 188 int pointerId) { | 180 int pointerId) { |
| 189 if (EventTarget* capturingTarget = getCapturingNode(pointerId)) | 181 if (EventTarget* capturingTarget = getCapturingNode(pointerId)) |
| (...skipping 101 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 291 } | 283 } |
| 292 | 284 |
| 293 void PointerEventManager::unblockTouchPointers() { | 285 void PointerEventManager::unblockTouchPointers() { |
| 294 m_inCanceledStateForPointerTypeTouch = false; | 286 m_inCanceledStateForPointerTypeTouch = false; |
| 295 } | 287 } |
| 296 | 288 |
| 297 WebInputEventResult PointerEventManager::handleTouchEvents( | 289 WebInputEventResult PointerEventManager::handleTouchEvents( |
| 298 const PlatformTouchEvent& event) { | 290 const PlatformTouchEvent& event) { |
| 299 if (event.type() == PlatformEvent::TouchScrollStarted) { | 291 if (event.type() == PlatformEvent::TouchScrollStarted) { |
| 300 blockTouchPointers(); | 292 blockTouchPointers(); |
| 301 m_touchEventManager->setTouchScrollStarted(); | |
| 302 return WebInputEventResult::HandledSystem; | 293 return WebInputEventResult::HandledSystem; |
| 303 } | 294 } |
| 304 | 295 |
| 305 bool newTouchSequence = true; | 296 bool newTouchSequence = true; |
| 306 for (const auto& touchPoint : event.touchPoints()) { | 297 for (const auto& touchPoint : event.touchPoints()) { |
| 307 if (touchPoint.state() != PlatformTouchPoint::TouchPressed) { | 298 if (touchPoint.state() != PlatformTouchPoint::TouchPressed) { |
| 308 newTouchSequence = false; | 299 newTouchSequence = false; |
| 309 break; | 300 break; |
| 310 } | 301 } |
| 311 } | 302 } |
| 312 if (newTouchSequence) | 303 if (newTouchSequence) |
| 313 unblockTouchPointers(); | 304 unblockTouchPointers(); |
| 305 |
| 306 // Do any necessary hit-tests and compute the event targets for all pointers |
| 307 // in the event. |
| 314 HeapVector<TouchEventManager::TouchInfo> touchInfos; | 308 HeapVector<TouchEventManager::TouchInfo> touchInfos; |
| 309 computeTouchTargets(event, touchInfos); |
| 310 |
| 311 // Any finger lifting is a user gesture only when it wasn't associated with a |
| 312 // scroll. |
| 313 // https://docs.google.com/document/d/1oF1T3O7_E4t1PYHV6gyCwHxOi3ystm0eSL5xZu7
nvOg/edit# |
| 314 // Re-use the same UserGesture for touchend and pointerup (but not for the |
| 315 // mouse events generated by GestureTap). |
| 316 // For the rare case of multi-finger scenarios spanning documents, it |
| 317 // seems extremely unlikely to matter which document the gesture is |
| 318 // associated with so just pick the first finger. |
| 319 RefPtr<UserGestureToken> possibleGestureToken; |
| 320 if (event.type() == PlatformEvent::TouchEnd && |
| 321 !m_inCanceledStateForPointerTypeTouch) { |
| 322 possibleGestureToken = |
| 323 DocumentUserGestureToken::create(touchInfos[0].targetFrame->document()); |
| 324 } |
| 325 UserGestureIndicator holder(possibleGestureToken); |
| 315 | 326 |
| 316 dispatchTouchPointerEvents(event, touchInfos); | 327 dispatchTouchPointerEvents(event, touchInfos); |
| 317 | 328 |
| 318 return m_touchEventManager->handleTouchEvent(event, touchInfos); | 329 return m_touchEventManager->handleTouchEvent(event, touchInfos); |
| 319 } | 330 } |
| 320 | 331 |
| 321 void PointerEventManager::dispatchTouchPointerEvents( | 332 void PointerEventManager::computeTouchTargets( |
| 322 const PlatformTouchEvent& event, | 333 const PlatformTouchEvent& event, |
| 323 HeapVector<TouchEventManager::TouchInfo>& touchInfos) { | 334 HeapVector<TouchEventManager::TouchInfo>& touchInfos) { |
| 324 // Iterate through the touch points, sending PointerEvents to the targets as | |
| 325 // required. | |
| 326 for (const auto& touchPoint : event.touchPoints()) { | 335 for (const auto& touchPoint : event.touchPoints()) { |
| 327 TouchEventManager::TouchInfo touchInfo; | 336 TouchEventManager::TouchInfo touchInfo; |
| 328 touchInfo.point = touchPoint; | 337 touchInfo.point = touchPoint; |
| 329 | 338 |
| 330 int pointerId = | 339 int pointerId = |
| 331 m_pointerEventFactory.getPointerEventId(touchPoint.pointerProperties()); | 340 m_pointerEventFactory.getPointerEventId(touchPoint.pointerProperties()); |
| 332 // Do the hit test either when the touch first starts or when the touch | 341 // Do the hit test either when the touch first starts or when the touch |
| 333 // is not captured. |m_pendingPointerCaptureTarget| indicates the target | 342 // is not captured. |m_pendingPointerCaptureTarget| indicates the target |
| 334 // that will be capturing this event. |m_pointerCaptureTarget| may not | 343 // that will be capturing this event. |m_pointerCaptureTarget| may not |
| 335 // have this target yet since the processing of that will be done right | 344 // have this target yet since the processing of that will be done right |
| (...skipping 30 matching lines...) Expand all Loading... |
| 366 } | 375 } |
| 367 } else { | 376 } else { |
| 368 // Set the target of pointer event to the captured node as this | 377 // Set the target of pointer event to the captured node as this |
| 369 // pointer is captured otherwise it would have gone to the if block | 378 // pointer is captured otherwise it would have gone to the if block |
| 370 // and perform a hit-test. | 379 // and perform a hit-test. |
| 371 touchInfo.touchNode = | 380 touchInfo.touchNode = |
| 372 m_pendingPointerCaptureTarget.get(pointerId)->toNode(); | 381 m_pendingPointerCaptureTarget.get(pointerId)->toNode(); |
| 373 touchInfo.targetFrame = touchInfo.touchNode->document().frame(); | 382 touchInfo.targetFrame = touchInfo.touchNode->document().frame(); |
| 374 } | 383 } |
| 375 | 384 |
| 385 touchInfos.append(touchInfo); |
| 386 } |
| 387 } |
| 388 |
| 389 void PointerEventManager::dispatchTouchPointerEvents( |
| 390 const PlatformTouchEvent& event, |
| 391 HeapVector<TouchEventManager::TouchInfo>& touchInfos) { |
| 392 // Iterate through the touch points, sending PointerEvents to the targets as |
| 393 // required. |
| 394 for (auto touchInfo : touchInfos) { |
| 395 const PlatformTouchPoint& touchPoint = touchInfo.point; |
| 376 // Do not send pointer events for stationary touches or null targetFrame | 396 // Do not send pointer events for stationary touches or null targetFrame |
| 377 if (touchInfo.touchNode && touchInfo.targetFrame && | 397 if (touchInfo.touchNode && touchInfo.targetFrame && |
| 378 touchPoint.state() != PlatformTouchPoint::TouchStationary && | 398 touchPoint.state() != PlatformTouchPoint::TouchStationary && |
| 379 !m_inCanceledStateForPointerTypeTouch) { | 399 !m_inCanceledStateForPointerTypeTouch) { |
| 380 FloatPoint pagePoint = touchInfo.targetFrame->view()->rootFrameToContents( | 400 FloatPoint pagePoint = touchInfo.targetFrame->view()->rootFrameToContents( |
| 381 touchInfo.point.pos()); | 401 touchInfo.point.pos()); |
| 382 float scaleFactor = 1.0f / touchInfo.targetFrame->pageZoomFactor(); | 402 float scaleFactor = 1.0f / touchInfo.targetFrame->pageZoomFactor(); |
| 383 FloatPoint scrollPosition(touchInfo.targetFrame->view()->scrollOffset()); | 403 FloatPoint scrollPosition(touchInfo.targetFrame->view()->scrollOffset()); |
| 384 FloatPoint framePoint = pagePoint.scaledBy(scaleFactor); | 404 FloatPoint framePoint = pagePoint.scaledBy(scaleFactor); |
| 385 framePoint.moveBy(scrollPosition.scaledBy(-scaleFactor)); | 405 framePoint.moveBy(scrollPosition.scaledBy(-scaleFactor)); |
| (...skipping 12 matching lines...) Expand all Loading... |
| 398 // fired from GestureTap & GestureLongPress (which are triggered by | 418 // fired from GestureTap & GestureLongPress (which are triggered by |
| 399 // single touches only), it is enough to queue the ids only for | 419 // single touches only), it is enough to queue the ids only for |
| 400 // primary pointers. | 420 // primary pointers. |
| 401 // TODO(mustaq): What about other cases (e.g. GestureTwoFingerTap)? | 421 // TODO(mustaq): What about other cases (e.g. GestureTwoFingerTap)? |
| 402 if (result != WebInputEventResult::NotHandled && | 422 if (result != WebInputEventResult::NotHandled && |
| 403 pointerEvent->type() == EventTypeNames::pointerdown && | 423 pointerEvent->type() == EventTypeNames::pointerdown && |
| 404 pointerEvent->isPrimary()) { | 424 pointerEvent->isPrimary()) { |
| 405 m_touchIdsForCanceledPointerdowns.append(event.uniqueTouchEventId()); | 425 m_touchIdsForCanceledPointerdowns.append(event.uniqueTouchEventId()); |
| 406 } | 426 } |
| 407 } | 427 } |
| 408 | |
| 409 touchInfos.append(touchInfo); | |
| 410 } | 428 } |
| 411 } | 429 } |
| 412 | 430 |
| 413 WebInputEventResult PointerEventManager::sendTouchPointerEvent( | 431 WebInputEventResult PointerEventManager::sendTouchPointerEvent( |
| 414 EventTarget* target, | 432 EventTarget* target, |
| 415 PointerEvent* pointerEvent) { | 433 PointerEvent* pointerEvent) { |
| 416 if (m_inCanceledStateForPointerTypeTouch) | 434 if (m_inCanceledStateForPointerTypeTouch) |
| 417 return WebInputEventResult::NotHandled; | 435 return WebInputEventResult::NotHandled; |
| 418 | 436 |
| 419 processCaptureAndPositionOfPointerEvent(pointerEvent, target); | 437 processCaptureAndPositionOfPointerEvent(pointerEvent, target); |
| (...skipping 280 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 700 return true; | 718 return true; |
| 701 } | 719 } |
| 702 return false; | 720 return false; |
| 703 } | 721 } |
| 704 | 722 |
| 705 EventTarget* PointerEventManager::getMouseCapturingNode() { | 723 EventTarget* PointerEventManager::getMouseCapturingNode() { |
| 706 return getCapturingNode(PointerEventFactory::s_mouseId); | 724 return getCapturingNode(PointerEventFactory::s_mouseId); |
| 707 } | 725 } |
| 708 | 726 |
| 709 } // namespace blink | 727 } // namespace blink |
| OLD | NEW |