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

Side by Side Diff: third_party/WebKit/Source/core/input/EventHandler.cpp

Issue 2389073002: Fix link's hover state if the link under scrollbar (Closed)
Patch Set: add test Created 4 years, 1 month 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 /* 1 /*
2 * Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights 2 * Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights
3 * reserved. 3 * reserved.
4 * Copyright (C) 2006 Alexey Proskuryakov (ap@webkit.org) 4 * Copyright (C) 2006 Alexey Proskuryakov (ap@webkit.org)
5 * Copyright (C) 2012 Digia Plc. and/or its subsidiary(-ies) 5 * Copyright (C) 2012 Digia Plc. and/or its subsidiary(-ies)
6 * 6 *
7 * Redistribution and use in source and binary forms, with or without 7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions 8 * modification, are permitted provided that the following conditions
9 * are met: 9 * are met:
10 * 1. Redistributions of source code must retain the above copyright 10 * 1. Redistributions of source code must retain the above copyright
(...skipping 260 matching lines...) Expand 10 before | Expand all | Expand 10 after
271 // the first layout because until then, there is nothing shown on the screen - 271 // the first layout because until then, there is nothing shown on the screen -
272 // the user can't have intentionally clicked on something belonging to this 272 // the user can't have intentionally clicked on something belonging to this
273 // page. Furthermore, mousemove events before the first layout should not 273 // page. Furthermore, mousemove events before the first layout should not
274 // lead to a premature layout() happening, which could show a flash of white. 274 // lead to a premature layout() happening, which could show a flash of white.
275 // See also the similar code in Document::performMouseEventHitTest. 275 // See also the similar code in Document::performMouseEventHitTest.
276 if (m_frame->contentLayoutItem().isNull() || !m_frame->view() || 276 if (m_frame->contentLayoutItem().isNull() || !m_frame->view() ||
277 !m_frame->view()->didFirstLayout()) 277 !m_frame->view()->didFirstLayout())
278 return result; 278 return result;
279 279
280 m_frame->contentLayoutItem().hitTest(result); 280 m_frame->contentLayoutItem().hitTest(result);
281 if (!request.readOnly()) 281 if (!request.readOnly()) {
282 m_frame->document()->updateHoverActiveState(request, result.innerElement()); 282 m_frame->document()->updateHoverActiveState(request, result.innerElement(),
283 result.scrollbar());
284 }
283 285
284 return result; 286 return result;
285 } 287 }
286 288
287 void EventHandler::stopAutoscroll() { 289 void EventHandler::stopAutoscroll() {
288 m_scrollManager->stopAutoscroll(); 290 m_scrollManager->stopAutoscroll();
289 } 291 }
290 292
291 // TODO(bokan): This should be merged with logicalScroll assuming 293 // TODO(bokan): This should be merged with logicalScroll assuming
292 // defaultSpaceEventHandler's chaining scroll can be done crossing frames. 294 // defaultSpaceEventHandler's chaining scroll can be done crossing frames.
(...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after
377 layoutViewItem.hitTest(result); 379 layoutViewItem.hitTest(result);
378 380
379 if (LocalFrame* frame = result.innerNodeFrame()) { 381 if (LocalFrame* frame = result.innerNodeFrame()) {
380 OptionalCursor optionalCursor = frame->eventHandler().selectCursor(result); 382 OptionalCursor optionalCursor = frame->eventHandler().selectCursor(result);
381 if (optionalCursor.isCursorChange()) { 383 if (optionalCursor.isCursorChange()) {
382 view->setCursor(optionalCursor.cursor()); 384 view->setCursor(optionalCursor.cursor());
383 } 385 }
384 } 386 }
385 } 387 }
386 388
389 Cursor::Type EventHandler::selectCursorTypeForTest(
390 const HitTestResult& result) {
391 return selectCursor(result).cursor().getType();
392 }
393
387 OptionalCursor EventHandler::selectCursor(const HitTestResult& result) { 394 OptionalCursor EventHandler::selectCursor(const HitTestResult& result) {
388 if (m_scrollManager->inResizeMode()) 395 if (m_scrollManager->inResizeMode())
389 return NoCursorChange; 396 return NoCursorChange;
390 397
391 Page* page = m_frame->page(); 398 Page* page = m_frame->page();
392 if (!page) 399 if (!page)
393 return NoCursorChange; 400 return NoCursorChange;
394 if (m_scrollManager->middleClickAutoscrollInProgress()) 401 if (m_scrollManager->middleClickAutoscrollInProgress())
395 return NoCursorChange; 402 return NoCursorChange;
396 403
(...skipping 125 matching lines...) Expand 10 before | Expand all | Expand 10 after
522 return grabCursor(); 529 return grabCursor();
523 case CURSOR_WEBKIT_GRABBING: 530 case CURSOR_WEBKIT_GRABBING:
524 return grabbingCursor(); 531 return grabbingCursor();
525 } 532 }
526 return pointerCursor(); 533 return pointerCursor();
527 } 534 }
528 535
529 OptionalCursor EventHandler::selectAutoCursor(const HitTestResult& result, 536 OptionalCursor EventHandler::selectAutoCursor(const HitTestResult& result,
530 Node* node, 537 Node* node,
531 const Cursor& iBeam) { 538 const Cursor& iBeam) {
539 if (result.scrollbar()) {
540 return pointerCursor();
541 }
542
532 bool editable = (node && hasEditableStyle(*node)); 543 bool editable = (node && hasEditableStyle(*node));
533 544
534 const bool isOverLink = 545 const bool isOverLink =
535 !selectionController().mouseDownMayStartSelect() && result.isOverLink(); 546 !selectionController().mouseDownMayStartSelect() && result.isOverLink();
536 if (useHandCursor(node, isOverLink)) 547 if (useHandCursor(node, isOverLink))
537 return handCursor(); 548 return handCursor();
538 549
539 bool inResizer = false; 550 bool inResizer = false;
540 LayoutObject* layoutObject = node ? node->layoutObject() : nullptr; 551 LayoutObject* layoutObject = node ? node->layoutObject() : nullptr;
541 if (layoutObject && m_frame->view()) { 552 if (layoutObject && m_frame->view()) {
(...skipping 262 matching lines...) Expand 10 before | Expand all | Expand 10 after
804 hitType |= HitTestRequest::Active | HitTestRequest::ReadOnly; 815 hitType |= HitTestRequest::Active | HitTestRequest::ReadOnly;
805 HitTestRequest request(hitType); 816 HitTestRequest request(hitType);
806 MouseEventWithHitTestResults mev = MouseEventWithHitTestResults( 817 MouseEventWithHitTestResults mev = MouseEventWithHitTestResults(
807 mouseEvent, HitTestResult(request, LayoutPoint())); 818 mouseEvent, HitTestResult(request, LayoutPoint()));
808 819
809 // We don't want to do a hit-test in forceLeave scenarios because there might 820 // We don't want to do a hit-test in forceLeave scenarios because there might
810 // actually be some other frame above this one at the specified co-ordinate. 821 // actually be some other frame above this one at the specified co-ordinate.
811 // So we must force the hit-test to fail, while still clearing hover/active 822 // So we must force the hit-test to fail, while still clearing hover/active
812 // state. 823 // state.
813 if (forceLeave) { 824 if (forceLeave) {
814 m_frame->document()->updateHoverActiveState(request, 0); 825 m_frame->document()->updateHoverActiveState(request, 0, false);
815 } else { 826 } else {
816 mev = EventHandlingUtil::performMouseEventHitTest(m_frame, request, 827 mev = EventHandlingUtil::performMouseEventHitTest(m_frame, request,
817 mouseEvent); 828 mouseEvent);
818 } 829 }
819 830
820 if (hoveredNode) 831 if (hoveredNode)
821 *hoveredNode = mev.hitTestResult(); 832 *hoveredNode = mev.hitTestResult();
822 833
823 Scrollbar* scrollbar = nullptr; 834 Scrollbar* scrollbar = nullptr;
824 835
(...skipping 693 matching lines...) Expand 10 before | Expand all | Expand 10 after
1518 1529
1519 LocalFrame* oldHoverFrame = toLocalFrame(owner->contentFrame()); 1530 LocalFrame* oldHoverFrame = toLocalFrame(owner->contentFrame());
1520 Document* doc = oldHoverFrame->document(); 1531 Document* doc = oldHoverFrame->document();
1521 if (!doc) 1532 if (!doc)
1522 break; 1533 break;
1523 1534
1524 oldHoverNodeInCurDoc = doc->hoverNode(); 1535 oldHoverNodeInCurDoc = doc->hoverNode();
1525 // If the old hovered frame is different from the new hovered frame. 1536 // If the old hovered frame is different from the new hovered frame.
1526 // we should clear the old hovered node from the old hovered frame. 1537 // we should clear the old hovered node from the old hovered frame.
1527 if (newHoverFrame != oldHoverFrame) 1538 if (newHoverFrame != oldHoverFrame)
1528 doc->updateHoverActiveState(request, nullptr); 1539 doc->updateHoverActiveState(request, nullptr, false);
1529 } 1540 }
1530 } 1541 }
1531 1542
1532 // Recursively set the new active/hover states on every frame in the chain of 1543 // Recursively set the new active/hover states on every frame in the chain of
1533 // innerElement. 1544 // innerElement.
1534 m_frame->document()->updateHoverActiveState(request, innerElement); 1545 m_frame->document()->updateHoverActiveState(request, innerElement, false);
1535 } 1546 }
1536 1547
1537 // Update the mouseover/mouseenter/mouseout/mouseleave events across all frames 1548 // Update the mouseover/mouseenter/mouseout/mouseleave events across all frames
1538 // for this gesture, before passing the targeted gesture event directly to a hit 1549 // for this gesture, before passing the targeted gesture event directly to a hit
1539 // frame. 1550 // frame.
1540 void EventHandler::updateGestureTargetNodeForMouseEvent( 1551 void EventHandler::updateGestureTargetNodeForMouseEvent(
1541 const GestureEventWithHitTestResults& targetedEvent) { 1552 const GestureEventWithHitTestResults& targetedEvent) {
1542 ASSERT(m_frame == m_frame->localFrameRoot()); 1553 ASSERT(m_frame == m_frame->localFrameRoot());
1543 1554
1544 // Behaviour of this function is as follows: 1555 // Behaviour of this function is as follows:
(...skipping 305 matching lines...) Expand 10 before | Expand all | Expand 10 after
1850 1861
1851 Node* targetNode = 1862 Node* targetNode =
1852 overrideTargetElement ? overrideTargetElement : doc->focusedElement(); 1863 overrideTargetElement ? overrideTargetElement : doc->focusedElement();
1853 if (!targetNode) 1864 if (!targetNode)
1854 targetNode = doc; 1865 targetNode = doc;
1855 1866
1856 // Use the focused node as the target for hover and active. 1867 // Use the focused node as the target for hover and active.
1857 HitTestRequest request(HitTestRequest::Active); 1868 HitTestRequest request(HitTestRequest::Active);
1858 HitTestResult result(request, locationInRootFrame); 1869 HitTestResult result(request, locationInRootFrame);
1859 result.setInnerNode(targetNode); 1870 result.setInnerNode(targetNode);
1860 doc->updateHoverActiveState(request, result.innerElement()); 1871 doc->updateHoverActiveState(request, result.innerElement(),
1872 result.scrollbar());
1861 1873
1862 // The contextmenu event is a mouse event even when invoked using the 1874 // The contextmenu event is a mouse event even when invoked using the
1863 // keyboard. This is required for web compatibility. 1875 // keyboard. This is required for web compatibility.
1864 PlatformEvent::EventType eventType = PlatformEvent::MousePressed; 1876 PlatformEvent::EventType eventType = PlatformEvent::MousePressed;
1865 if (m_frame->settings() && m_frame->settings()->showContextMenuOnMouseUp()) 1877 if (m_frame->settings() && m_frame->settings()->showContextMenuOnMouseUp())
1866 eventType = PlatformEvent::MouseReleased; 1878 eventType = PlatformEvent::MouseReleased;
1867 1879
1868 PlatformMouseEvent mouseEvent( 1880 PlatformMouseEvent mouseEvent(
1869 locationInRootFrame, globalPosition, 1881 locationInRootFrame, globalPosition,
1870 WebPointerProperties::Button::NoButton, eventType, /* clickCount */ 0, 1882 WebPointerProperties::Button::NoButton, eventType, /* clickCount */ 0,
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
1916 ASSERT(m_frame); 1928 ASSERT(m_frame);
1917 ASSERT(m_frame->document()); 1929 ASSERT(m_frame->document());
1918 1930
1919 if (LayoutViewItem layoutItem = m_frame->contentLayoutItem()) { 1931 if (LayoutViewItem layoutItem = m_frame->contentLayoutItem()) {
1920 if (FrameView* view = m_frame->view()) { 1932 if (FrameView* view = m_frame->view()) {
1921 HitTestRequest request(HitTestRequest::Move); 1933 HitTestRequest request(HitTestRequest::Move);
1922 HitTestResult result(request, 1934 HitTestResult result(request,
1923 view->rootFrameToContents( 1935 view->rootFrameToContents(
1924 m_mouseEventManager->lastKnownMousePosition())); 1936 m_mouseEventManager->lastKnownMousePosition()));
1925 layoutItem.hitTest(result); 1937 layoutItem.hitTest(result);
1926 m_frame->document()->updateHoverActiveState(request, 1938 m_frame->document()->updateHoverActiveState(
1927 result.innerElement()); 1939 request, result.innerElement(), result.scrollbar());
1928 } 1940 }
1929 } 1941 }
1930 } 1942 }
1931 1943
1932 void EventHandler::activeIntervalTimerFired(TimerBase*) { 1944 void EventHandler::activeIntervalTimerFired(TimerBase*) {
1933 TRACE_EVENT0("input", "EventHandler::activeIntervalTimerFired"); 1945 TRACE_EVENT0("input", "EventHandler::activeIntervalTimerFired");
1934 m_activeIntervalTimer.stop(); 1946 m_activeIntervalTimer.stop();
1935 1947
1936 if (m_frame && m_frame->document() && m_lastDeferredTapElement) { 1948 if (m_frame && m_frame->document() && m_lastDeferredTapElement) {
1937 // FIXME: Enable condition when http://crbug.com/226842 lands 1949 // FIXME: Enable condition when http://crbug.com/226842 lands
1938 // m_lastDeferredTapElement.get() == m_frame->document()->activeElement() 1950 // m_lastDeferredTapElement.get() == m_frame->document()->activeElement()
1939 HitTestRequest request(HitTestRequest::TouchEvent | 1951 HitTestRequest request(HitTestRequest::TouchEvent |
1940 HitTestRequest::Release); 1952 HitTestRequest::Release);
1941 m_frame->document()->updateHoverActiveState(request, 1953 m_frame->document()->updateHoverActiveState(
1942 m_lastDeferredTapElement.get()); 1954 request, m_lastDeferredTapElement.get(), false);
1943 } 1955 }
1944 m_lastDeferredTapElement = nullptr; 1956 m_lastDeferredTapElement = nullptr;
1945 } 1957 }
1946 1958
1947 void EventHandler::notifyElementActivated() { 1959 void EventHandler::notifyElementActivated() {
1948 // Since another element has been set to active, stop current timer and clear 1960 // Since another element has been set to active, stop current timer and clear
1949 // reference. 1961 // reference.
1950 m_activeIntervalTimer.stop(); 1962 m_activeIntervalTimer.stop();
1951 m_lastDeferredTapElement = nullptr; 1963 m_lastDeferredTapElement = nullptr;
1952 } 1964 }
(...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after
2086 } 2098 }
2087 2099
2088 FrameHost* EventHandler::frameHost() const { 2100 FrameHost* EventHandler::frameHost() const {
2089 if (!m_frame->page()) 2101 if (!m_frame->page())
2090 return nullptr; 2102 return nullptr;
2091 2103
2092 return &m_frame->page()->frameHost(); 2104 return &m_frame->page()->frameHost();
2093 } 2105 }
2094 2106
2095 } // namespace blink 2107 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698