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

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

Issue 1635863006: Pointerevent capture APIs (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Created 4 years, 10 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 /* 1 /*
2 * Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserv ed. 2 * Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserv ed.
3 * Copyright (C) 2006 Alexey Proskuryakov (ap@webkit.org) 3 * Copyright (C) 2006 Alexey Proskuryakov (ap@webkit.org)
4 * Copyright (C) 2012 Digia Plc. and/or its subsidiary(-ies) 4 * Copyright (C) 2012 Digia Plc. and/or its subsidiary(-ies)
5 * 5 *
6 * Redistribution and use in source and binary forms, with or without 6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions 7 * modification, are permitted provided that the following conditions
8 * are met: 8 * are met:
9 * 1. Redistributions of source code must retain the above copyright 9 * 1. Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer. 10 * notice, this list of conditions and the following disclaimer.
(...skipping 1643 matching lines...) Expand 10 before | Expand all | Expand 10 after
1654 1654
1655 bool dispatchResult = target->dispatchEvent(pointerEvent.get()); 1655 bool dispatchResult = target->dispatchEvent(pointerEvent.get());
1656 return eventToEventResult(pointerEvent, dispatchResult); 1656 return eventToEventResult(pointerEvent, dispatchResult);
1657 } 1657 }
1658 1658
1659 void EventHandler::sendNodeTransitionEvents(Node* exitedNode, Node* enteredNode, 1659 void EventHandler::sendNodeTransitionEvents(Node* exitedNode, Node* enteredNode,
1660 const PlatformMouseEvent& mouseEvent) 1660 const PlatformMouseEvent& mouseEvent)
1661 { 1661 {
1662 ASSERT(exitedNode != enteredNode); 1662 ASSERT(exitedNode != enteredNode);
1663 1663
1664 // Dispatch pointerout/mouseout events 1664 if (m_pointerEventManager.getMouseCapturingNode()) {
1665 if (isNodeInDocument(exitedNode)) { 1665 EventTarget* target = m_pointerEventManager.getMouseCapturingNode();
mustaq 2016/02/06 04:36:31 s/target/capturingNode/
Navid Zolghadr 2016/02/08 15:58:43 Done.
1666 sendPointerAndMouseTransitionEvents(exitedNode, EventTypeNames::mouseout , mouseEvent, enteredNode, false); 1666 if (target == exitedNode)
1667 enteredNode = nullptr;
1668 else if (target == enteredNode)
1669 exitedNode = nullptr;
mustaq 2016/02/06 04:36:31 Perhaps this won't happen but not sure: any chance
Navid Zolghadr 2016/02/08 15:58:43 Do you have any particular scenario in mind? I can
1670 else
1671 return;
1667 } 1672 }
1668 1673
1669 // A note on mouseenter and mouseleave: These are non-bubbling events, and t hey are dispatched if there 1674 // A note on mouseenter and mouseleave: These are non-bubbling events, and t hey are dispatched if there
1670 // is a capturing event handler on an ancestor or a normal event handler on the element itself. This special 1675 // is a capturing event handler on an ancestor or a normal event handler on the element itself. This special
1671 // handling is necessary to avoid O(n^2) capturing event handler checks. 1676 // handling is necessary to avoid O(n^2) capturing event handler checks.
1672 // 1677 //
1673 // Note, however, that this optimization can possibly cause some unanswere d/missing/redundant mouseenter or 1678 // Note, however, that this optimization can possibly cause some unanswere d/missing/redundant mouseenter or
1674 // mouseleave events in certain contrived eventhandling scenarios, e.g., whe n: 1679 // mouseleave events in certain contrived eventhandling scenarios, e.g., whe n:
1675 // - the mouseleave handler for a node sets the only capturing-mouseleave-li stener in its ancestor, or 1680 // - the mouseleave handler for a node sets the only capturing-mouseleave-li stener in its ancestor, or
1676 // - DOM mods in any mouseenter/mouseleave handler changes the common ancest or of exited & entered nodes, etc. 1681 // - DOM mods in any mouseenter/mouseleave handler changes the common ancest or of exited & entered nodes, etc.
(...skipping 12 matching lines...) Expand all
1689 exitedAncestors.append(node); 1694 exitedAncestors.append(node);
1690 } 1695 }
1691 } 1696 }
1692 if (isNodeInDocument(enteredNode)) { 1697 if (isNodeInDocument(enteredNode)) {
1693 enteredNode->updateDistribution(); 1698 enteredNode->updateDistribution();
1694 for (Node* node = enteredNode; node; node = ComposedTreeTraversal::paren t(*node)) { 1699 for (Node* node = enteredNode; node; node = ComposedTreeTraversal::paren t(*node)) {
1695 enteredAncestors.append(node); 1700 enteredAncestors.append(node);
1696 } 1701 }
1697 } 1702 }
1698 1703
1704 // Dispatch pointerout/mouseout events
1705 if (isNodeInDocument(exitedNode)) {
1706 sendPointerAndMouseTransitionEvents(exitedNode, EventTypeNames::mouseout , mouseEvent, enteredNode, false);
1707 }
1708
1699 size_t numExitedAncestors = exitedAncestors.size(); 1709 size_t numExitedAncestors = exitedAncestors.size();
1700 size_t numEnteredAncestors = enteredAncestors.size(); 1710 size_t numEnteredAncestors = enteredAncestors.size();
1701 1711
1702 size_t exitedAncestorIndex = numExitedAncestors; 1712 size_t exitedAncestorIndex = numExitedAncestors;
1703 size_t enteredAncestorIndex = numEnteredAncestors; 1713 size_t enteredAncestorIndex = numEnteredAncestors;
1704 for (size_t j = 0; j < numExitedAncestors; j++) { 1714 for (size_t j = 0; j < numExitedAncestors; j++) {
1705 for (size_t i = 0; i < numEnteredAncestors; i++) { 1715 for (size_t i = 0; i < numEnteredAncestors; i++) {
1706 if (exitedAncestors[j] == enteredAncestors[i]) { 1716 if (exitedAncestors[j] == enteredAncestors[i]) {
1707 exitedAncestorIndex = j; 1717 exitedAncestorIndex = j;
1708 enteredAncestorIndex = i; 1718 enteredAncestorIndex = i;
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after
1751 { 1761 {
1752 updateMouseEventTargetNode(targetNode, mouseEvent); 1762 updateMouseEventTargetNode(targetNode, mouseEvent);
1753 if (!m_nodeUnderMouse) 1763 if (!m_nodeUnderMouse)
1754 return WebInputEventResult::NotHandled; 1764 return WebInputEventResult::NotHandled;
1755 1765
1756 RefPtrWillBeRawPtr<MouseEvent> event = MouseEvent::create(eventType, m_nodeU nderMouse->document().domWindow(), mouseEvent, clickCount, nullptr); 1766 RefPtrWillBeRawPtr<MouseEvent> event = MouseEvent::create(eventType, m_nodeU nderMouse->document().domWindow(), mouseEvent, clickCount, nullptr);
1757 bool dispatchResult = m_nodeUnderMouse->dispatchEvent(event); 1767 bool dispatchResult = m_nodeUnderMouse->dispatchEvent(event);
1758 return eventToEventResult(event, dispatchResult); 1768 return eventToEventResult(event, dispatchResult);
1759 } 1769 }
1760 1770
1771 bool EventHandler::isPointerEventActive(int pointerId)
1772 {
1773 return m_pointerEventManager.isActive(pointerId);
1774 }
1775
1776 void EventHandler::setPointerCapture(int pointerId, EventTarget* target)
1777 {
1778 m_pointerEventManager.setPointerCapture(pointerId, target);
1779 }
1780
1781 void EventHandler::releasePointerCapture(int pointerId, EventTarget* target)
1782 {
1783 m_pointerEventManager.releasePointerCapture(pointerId, target);
1784 }
1785
1786 void EventHandler::elementRemoved(EventTarget* target)
1787 {
1788 m_pointerEventManager.elementRemoved(target);
1789 }
1790
1761 EventTarget* EventHandler::getEffectiveTargetForPointerEvent( 1791 EventTarget* EventHandler::getEffectiveTargetForPointerEvent(
1762 EventTarget* target, PassRefPtrWillBeRawPtr<PointerEvent> pointerEvent) 1792 EventTarget* target, PassRefPtrWillBeRawPtr<PointerEvent> pointerEvent)
1763 { 1793 {
1764 EventTarget* capturingNode = m_pointerEventManager.getCapturingNode(pointerE vent.get()); 1794 EventTarget* capturingNode = m_pointerEventManager.getCapturingNode(pointerE vent.get());
1765 if (capturingNode) 1795 if (capturingNode)
1766 target = capturingNode; 1796 target = capturingNode;
1767 return target; 1797 return target;
1768 } 1798 }
1769 1799
1770 void EventHandler::sendPointerAndMouseTransitionEvents(Node* target, const Atomi cString& mouseEventType, 1800 void EventHandler::sendPointerAndMouseTransitionEvents(Node* target, const Atomi cString& mouseEventType,
1771 const PlatformMouseEvent& mouseEvent, Node* relatedTarget, bool checkForList ener) 1801 const PlatformMouseEvent& mouseEvent, Node* relatedTarget, bool checkForList ener)
1772 { 1802 {
1773 ASSERT(mouseEventType == EventTypeNames::mouseenter 1803 ASSERT(mouseEventType == EventTypeNames::mouseenter
1774 || mouseEventType == EventTypeNames::mouseleave 1804 || mouseEventType == EventTypeNames::mouseleave
1775 || mouseEventType == EventTypeNames::mouseover 1805 || mouseEventType == EventTypeNames::mouseover
1776 || mouseEventType == EventTypeNames::mouseout); 1806 || mouseEventType == EventTypeNames::mouseout);
1777 1807
1778 AtomicString pointerEventType = pointerEventNameForMouseEventName(mouseEvent Type); 1808 AtomicString pointerEventType = pointerEventNameForMouseEventName(mouseEvent Type);
1779 RefPtrWillBeRawPtr<PointerEvent> pointerEvent = m_pointerEventManager.create (pointerEventType, 1809 RefPtrWillBeRawPtr<PointerEvent> pointerEvent = m_pointerEventManager.create (pointerEventType,
1780 mouseEvent, relatedTarget, m_frame->document()->domWindow()); 1810 mouseEvent, relatedTarget, m_frame->document()->domWindow());
1781 1811
1782 // Suppress these events if the target is not the capturing element 1812
1783 if (target != getEffectiveTargetForPointerEvent(target, pointerEvent)) 1813 int isAncestor = false;
mustaq 2016/02/06 04:36:31 I guess you can avoid the loop below for mouseover
Navid Zolghadr 2016/02/08 15:58:43 I believe I can get rid of this for now as the cha
1814 for (Node* node = target; node; node = ComposedTreeTraversal::parent(*node)) {
1815 if (node == target) {
mustaq 2016/02/06 04:36:31 I think the loop should start at node = capturingN
1816 isAncestor = true;
1817 break;
1818 }
1819 }
1820 // Suppress these events if the target is not the capturing element inclusiv e ancestors
mustaq 2016/02/06 04:36:31 Is it clearer? "...if target is not an (inclusive)
1821 if (!isAncestor)
1784 return; 1822 return;
1785 1823
1786 if (!checkForListener || target->hasEventListeners(pointerEventType)) 1824 if (!checkForListener || target->hasEventListeners(pointerEventType))
1787 dispatchPointerEvent(target, pointerEvent); 1825 dispatchPointerEvent(target, pointerEvent);
1788 1826
1789 if (!checkForListener || target->hasEventListeners(mouseEventType)) 1827 if (!checkForListener || target->hasEventListeners(mouseEventType))
1790 target->dispatchMouseEvent(mouseEvent, mouseEventType, 0, relatedTarget) ; 1828 target->dispatchMouseEvent(mouseEvent, mouseEventType, 0, relatedTarget) ;
1791 } 1829 }
1792 1830
1793 // TODO(mustaq): Make PE drive ME dispatch & bookkeeping in EventHandler. 1831 // TODO(mustaq): Make PE drive ME dispatch & bookkeeping in EventHandler.
(...skipping 23 matching lines...) Expand all
1817 1855
1818 if (result != WebInputEventResult::NotHandled && pointerEventType == EventTy peNames::pointerdown) 1856 if (result != WebInputEventResult::NotHandled && pointerEventType == EventTy peNames::pointerdown)
1819 m_preventMouseEventForPointerTypeMouse = true; 1857 m_preventMouseEventForPointerTypeMouse = true;
1820 1858
1821 if (!m_preventMouseEventForPointerTypeMouse) { 1859 if (!m_preventMouseEventForPointerTypeMouse) {
1822 RefPtrWillBeRawPtr<MouseEvent> event = MouseEvent::create(mouseEventType , m_nodeUnderMouse->document().domWindow(), mouseEvent, clickCount, nullptr); 1860 RefPtrWillBeRawPtr<MouseEvent> event = MouseEvent::create(mouseEventType , m_nodeUnderMouse->document().domWindow(), mouseEvent, clickCount, nullptr);
1823 bool dispatchResult = target->dispatchEvent(event); 1861 bool dispatchResult = target->dispatchEvent(event);
1824 result = mergeEventResult(result, eventToEventResult(event, dispatchResu lt)); 1862 result = mergeEventResult(result, eventToEventResult(event, dispatchResu lt));
1825 } 1863 }
1826 1864
1865 if (pointerEvent->buttons() == 0)
1866 m_pointerEventManager.implicitReleasePointerCapture(pointerEvent->pointe rId());
1867
1827 return result; 1868 return result;
1828 } 1869 }
1829 1870
1830 WebInputEventResult EventHandler::handleMouseFocus(const MouseEventWithHitTestRe sults& targetedEvent, InputDeviceCapabilities* sourceCapabilities) 1871 WebInputEventResult EventHandler::handleMouseFocus(const MouseEventWithHitTestRe sults& targetedEvent, InputDeviceCapabilities* sourceCapabilities)
1831 { 1872 {
1832 // If clicking on a frame scrollbar, do not mess up with content focus. 1873 // If clicking on a frame scrollbar, do not mess up with content focus.
1833 if (targetedEvent.hitTestResult().scrollbar() && m_frame->contentLayoutObjec t()) { 1874 if (targetedEvent.hitTestResult().scrollbar() && m_frame->contentLayoutObjec t()) {
1834 if (targetedEvent.hitTestResult().scrollbar()->scrollableArea() == m_fra me->contentLayoutObject()->scrollableArea()) 1875 if (targetedEvent.hitTestResult().scrollbar()->scrollableArea() == m_fra me->contentLayoutObject()->scrollableArea())
1835 return WebInputEventResult::NotHandled; 1876 return WebInputEventResult::NotHandled;
1836 } 1877 }
(...skipping 2330 matching lines...) Expand 10 before | Expand all | Expand 10 after
4167 PlatformEvent::Modifiers EventHandler::accessKeyModifiers() 4208 PlatformEvent::Modifiers EventHandler::accessKeyModifiers()
4168 { 4209 {
4169 #if OS(MACOSX) 4210 #if OS(MACOSX)
4170 return static_cast<PlatformEvent::Modifiers>(PlatformEvent::CtrlKey | Platfo rmEvent::AltKey); 4211 return static_cast<PlatformEvent::Modifiers>(PlatformEvent::CtrlKey | Platfo rmEvent::AltKey);
4171 #else 4212 #else
4172 return PlatformEvent::AltKey; 4213 return PlatformEvent::AltKey;
4173 #endif 4214 #endif
4174 } 4215 }
4175 4216
4176 } // namespace blink 4217 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698