| 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/BoundaryEventDispatcher.h" | 5 #include "core/input/BoundaryEventDispatcher.h" |
| 6 | 6 |
| 7 #include "core/dom/Node.h" | 7 #include "core/dom/Node.h" |
| 8 #include "core/dom/shadow/FlatTreeTraversal.h" | 8 #include "core/dom/shadow/FlatTreeTraversal.h" |
| 9 #include "core/input/EventHandlingUtil.h" |
| 9 | 10 |
| 10 namespace blink { | 11 namespace blink { |
| 11 | 12 |
| 12 namespace { | 13 namespace { |
| 13 | 14 |
| 14 bool IsInDocument(EventTarget* target) { | |
| 15 return target && target->ToNode() && target->ToNode()->isConnected(); | |
| 16 } | |
| 17 | |
| 18 void BuildAncestorChain(EventTarget* target, | 15 void BuildAncestorChain(EventTarget* target, |
| 19 HeapVector<Member<Node>, 20>* ancestors) { | 16 HeapVector<Member<Node>, 20>* ancestors) { |
| 20 if (!IsInDocument(target)) | 17 if (!EventHandlingUtil::IsInDocument(target)) |
| 21 return; | 18 return; |
| 22 Node* target_node = target->ToNode(); | 19 Node* target_node = target->ToNode(); |
| 23 DCHECK(target_node); | 20 DCHECK(target_node); |
| 24 target_node->UpdateDistribution(); | 21 target_node->UpdateDistribution(); |
| 25 // Index 0 element in the ancestors arrays will be the corresponding | 22 // Index 0 element in the ancestors arrays will be the corresponding |
| 26 // target. So the root of their document will be their last element. | 23 // target. So the root of their document will be their last element. |
| 27 for (Node* node = target_node; node; node = FlatTreeTraversal::Parent(*node)) | 24 for (Node* node = target_node; node; node = FlatTreeTraversal::Parent(*node)) |
| 28 ancestors->push_back(node); | 25 ancestors->push_back(node); |
| 29 } | 26 } |
| 30 | 27 |
| (...skipping 27 matching lines...) Expand all Loading... |
| 58 } | 55 } |
| 59 | 56 |
| 60 } // namespace | 57 } // namespace |
| 61 | 58 |
| 62 void BoundaryEventDispatcher::SendBoundaryEvents(EventTarget* exited_target, | 59 void BoundaryEventDispatcher::SendBoundaryEvents(EventTarget* exited_target, |
| 63 EventTarget* entered_target) { | 60 EventTarget* entered_target) { |
| 64 if (exited_target == entered_target) | 61 if (exited_target == entered_target) |
| 65 return; | 62 return; |
| 66 | 63 |
| 67 // Dispatch out event | 64 // Dispatch out event |
| 68 if (IsInDocument(exited_target)) | 65 if (EventHandlingUtil::IsInDocument(exited_target)) |
| 69 DispatchOut(exited_target, entered_target); | 66 DispatchOut(exited_target, entered_target); |
| 70 | 67 |
| 71 // Create lists of all exited/entered ancestors, locate the common ancestor | 68 // Create lists of all exited/entered ancestors, locate the common ancestor |
| 72 // Based on httparchive, in more than 97% cases the depth of DOM is less | 69 // Based on httparchive, in more than 97% cases the depth of DOM is less |
| 73 // than 20. | 70 // than 20. |
| 74 HeapVector<Member<Node>, 20> exited_ancestors; | 71 HeapVector<Member<Node>, 20> exited_ancestors; |
| 75 HeapVector<Member<Node>, 20> entered_ancestors; | 72 HeapVector<Member<Node>, 20> entered_ancestors; |
| 76 size_t exited_ancestors_common_parent_index = 0; | 73 size_t exited_ancestors_common_parent_index = 0; |
| 77 size_t entered_ancestors_common_parent_index = 0; | 74 size_t entered_ancestors_common_parent_index = 0; |
| 78 | 75 |
| (...skipping 29 matching lines...) Expand all Loading... |
| 108 break; | 105 break; |
| 109 } | 106 } |
| 110 } | 107 } |
| 111 | 108 |
| 112 // Dispatch leave events, in child-to-parent order. | 109 // Dispatch leave events, in child-to-parent order. |
| 113 for (size_t j = 0; j < exited_ancestors_common_parent_index; j++) | 110 for (size_t j = 0; j < exited_ancestors_common_parent_index; j++) |
| 114 DispatchLeave(exited_ancestors[j], entered_target, | 111 DispatchLeave(exited_ancestors[j], entered_target, |
| 115 !exited_node_has_capturing_ancestor); | 112 !exited_node_has_capturing_ancestor); |
| 116 | 113 |
| 117 // Dispatch over event | 114 // Dispatch over event |
| 118 if (IsInDocument(entered_target)) | 115 if (EventHandlingUtil::IsInDocument(entered_target)) |
| 119 DispatchOver(entered_target, exited_target); | 116 DispatchOver(entered_target, exited_target); |
| 120 | 117 |
| 121 // Defer locating capturing enter listener until /after/ dispatching the leave | 118 // Defer locating capturing enter listener until /after/ dispatching the leave |
| 122 // events because the leave handlers might set a capturing enter handler. | 119 // events because the leave handlers might set a capturing enter handler. |
| 123 bool entered_node_has_capturing_ancestor = false; | 120 bool entered_node_has_capturing_ancestor = false; |
| 124 const AtomicString& enter_event = GetEnterEvent(); | 121 const AtomicString& enter_event = GetEnterEvent(); |
| 125 for (size_t i = 0; i < entered_ancestors.size(); i++) { | 122 for (size_t i = 0; i < entered_ancestors.size(); i++) { |
| 126 if (entered_ancestors[i]->HasCapturingEventListeners(enter_event)) { | 123 if (entered_ancestors[i]->HasCapturingEventListeners(enter_event)) { |
| 127 entered_node_has_capturing_ancestor = true; | 124 entered_node_has_capturing_ancestor = true; |
| 128 break; | 125 break; |
| 129 } | 126 } |
| 130 } | 127 } |
| 131 | 128 |
| 132 // Dispatch enter events, in parent-to-child order. | 129 // Dispatch enter events, in parent-to-child order. |
| 133 for (size_t i = entered_ancestors_common_parent_index; i > 0; i--) | 130 for (size_t i = entered_ancestors_common_parent_index; i > 0; i--) |
| 134 DispatchEnter(entered_ancestors[i - 1], exited_target, | 131 DispatchEnter(entered_ancestors[i - 1], exited_target, |
| 135 !entered_node_has_capturing_ancestor); | 132 !entered_node_has_capturing_ancestor); |
| 136 } | 133 } |
| 137 | 134 |
| 138 } // namespace blink | 135 } // namespace blink |
| OLD | NEW |