Changeset 243244 in webkit
- Timestamp:
- Mar 20, 2019 2:55:05 PM (5 years ago)
- Location:
- trunk
- Files:
-
- 18 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/LayoutTests/ChangeLog
r243242 r243244 1 2019-03-20 Devin Rousso <drousso@apple.com> 2 3 Web Inspector: DOM: include window as part of any event listener chain 4 https://bugs.webkit.org/show_bug.cgi?id=195730 5 <rdar://problem/48916872> 6 7 Reviewed by Timothy Hatcher. 8 9 * inspector/dom/getEventListenersForNode.html: 10 * inspector/dom/getEventListenersForNode-expected.txt: 11 * inspector/dom/setEventListenerDisabled.html: 12 * inspector/dom/event-listener-add-remove.html: 13 1 14 2019-03-20 Devin Rousso <drousso@apple.com> 2 15 -
trunk/LayoutTests/inspector/dom/event-listener-add-remove.html
r236766 r243244 54 54 55 55 function logListeners(expectedCount) { 56 return DOMAgent.getEventListenersForNode(node.id).then((payload) => { 57 InspectorTest.expectEqual(payload.listeners.length, expectedCount, `There should be ${expectedCount} event listeners.`); 58 59 for (let eventListener of payload.listeners) 56 return DOMAgent.getEventListenersForNode(node.id).then(({listeners}) => { 57 listeners = listeners.filter((listener) => listener.nodeId === node.id); 58 59 InspectorTest.expectEqual(listeners.length, expectedCount, `There should be ${expectedCount} event listeners.`); 60 61 for (let eventListener of listeners) 60 62 InspectorTest.log(` - "${eventListener.type}"`); 61 63 }); … … 68 70 description: "Test that the document has no event listeners.", 69 71 test(resolve, reject) { 70 DOMAgent.getEventListenersForNode(node.id).then((payload) => { 71 InspectorTest.expectEqual(payload.listeners.length, 0, "There should be no event listeners."); 72 73 for (let eventListener of payload.listeners) 72 DOMAgent.getEventListenersForNode(node.id).then(({listeners}) => { 73 listeners = listeners.filter((listener) => listener.nodeId === node.id); 74 75 InspectorTest.expectEqual(listeners.length, 0, "There should be no event listeners."); 76 77 for (let eventListener of listeners) 74 78 InspectorTest.log(eventListener.type); 75 79 }).then(resolve, reject); -
trunk/LayoutTests/inspector/dom/getEventListenersForNode-expected.txt
r241110 r243244 5 5 -- Running test case: DOM.getEventListenersForNode.Basic 6 6 Event: A 7 Node: body7 Target: body 8 8 Capture: true 9 9 Attribute: false 10 10 Handler Name: bodyA 11 PASS:The Event Listener has a source location.11 The Event Listener has a source location. 12 12 13 13 Event: B 14 Node: body14 Target: body 15 15 Capture: true 16 16 Attribute: false 17 PASS:The Event Listener has a source location.17 The Event Listener has a source location. 18 18 19 19 Event: E 20 Node: div#x20 Target: div#x 21 21 Capture: false 22 22 Attribute: false 23 23 Handler Name: ObjectEventHandler 24 PASS:The Event Listener has a source location.24 The Event Listener has a source location. 25 25 26 26 Event: D 27 Node: div#x27 Target: div#x 28 28 Capture: false 29 29 Attribute: false 30 30 Handler Name: handleEvent 31 PASS:The Event Listener has a source location.31 The Event Listener has a source location. 32 32 33 33 Event: C 34 Node: div#x34 Target: div#x 35 35 Capture: false 36 36 Attribute: false 37 PASS:The Event Listener has a source location.37 The Event Listener has a source location. 38 38 39 39 Event: B 40 Node: div#x40 Target: div#x 41 41 Capture: false 42 42 Attribute: false 43 43 Handler Name: xB 44 44 Once: true 45 PASS:The Event Listener has a source location.45 The Event Listener has a source location. 46 46 47 47 Event: A 48 Node: div#x48 Target: div#x 49 49 Capture: false 50 50 Attribute: false 51 51 Handler Name: xA 52 PASS:The Event Listener has a source location.52 The Event Listener has a source location. 53 53 54 54 Event: click 55 Node: div#x55 Target: div#x 56 56 Capture: false 57 57 Attribute: true 58 58 Handler Name: onclick 59 PASS:The Event Listener has a source location.59 The Event Listener has a source location. 60 60 61 61 Event: B 62 Node: #document62 Target: #document 63 63 Capture: false 64 64 Attribute: false 65 65 Passive: true 66 PASS:The Event Listener has a source location.66 The Event Listener has a source location. 67 67 68 68 Event: A 69 Node: #document69 Target: #document 70 70 Capture: false 71 71 Attribute: false 72 72 Handler Name: documentA 73 73 Passive: true 74 PASS: The Event Listener has a source location. 74 The Event Listener has a source location. 75 76 Event: load 77 Target: window 78 Capture: false 79 Attribute: true 80 Handler Name: onload 81 The Event Listener has a source location. 82 83 Event: error 84 Target: window 85 Capture: false 86 Attribute: true 75 87 76 88 -
trunk/LayoutTests/inspector/dom/getEventListenersForNode.html
r241110 r243244 20 20 21 21 for (let eventListener of eventListeners) { 22 let node = WI.domManager.nodeForId(eventListener.nodeId);23 24 25 22 InspectorTest.log(`Event: ${eventListener.type}`); 26 InspectorTest.log(`Node: ${node.displayName}`); 23 if (eventListener.nodeId) { 24 let node = WI.domManager.nodeForId(eventListener.nodeId); 25 InspectorTest.log(`Target: ${node.displayName}`); 26 } 27 if (eventListener.onWindow) 28 InspectorTest.log("Target: window"); 27 29 InspectorTest.log(`Capture: ${eventListener.useCapture}`); 28 30 InspectorTest.log(`Attribute: ${eventListener.isAttribute}`); … … 34 36 if (eventListener.once) 35 37 InspectorTest.log(`Once: ${eventListener.once}`); 36 37 InspectorTest.expectThat(eventListener.location,"The Event Listener has a source location.");38 if (eventListener.location) 39 InspectorTest.log("The Event Listener has a source location."); 38 40 39 41 InspectorTest.log(""); -
trunk/LayoutTests/inspector/dom/setEventListenerDisabled.html
r236766 r243244 17 17 function logListener() { 18 18 return DOMAgent.getEventListenersForNode(clickEventListener.nodeId).then(({listeners}) => { 19 listeners = listeners.filter((listener) => listener.nodeId === clickEventListener.nodeId); 19 20 InspectorTest.assert(listeners.length === 1, "There should only be one event listener."); 20 21 InspectorTest.assert(listeners[0].type === "click", `There event listener should be for "click".`); -
trunk/Source/JavaScriptCore/ChangeLog
r243243 r243244 1 2019-03-20 Devin Rousso <drousso@apple.com> 2 3 Web Inspector: DOM: include window as part of any event listener chain 4 https://bugs.webkit.org/show_bug.cgi?id=195730 5 <rdar://problem/48916872> 6 7 Reviewed by Timothy Hatcher. 8 9 * inspector/protocol/DOM.json: 10 Modify `DOM.getEventListenersForNode` to not save the handler object, as that was never 11 used by the frontend. Add an `onWindow` optional property to `DOM.EventListener` that is set 12 when the event listener was retrieved from the `window` object. 13 1 14 2019-03-20 Devin Rousso <drousso@apple.com> 2 15 -
trunk/Source/JavaScriptCore/inspector/protocol/DOM.json
r243207 r243244 88 88 { "name": "useCapture", "type": "boolean", "description": "<code>EventListener</code>'s useCapture." }, 89 89 { "name": "isAttribute", "type": "boolean", "description": "<code>EventListener</code>'s isAttribute." }, 90 { "name": "nodeId", "$ref": "NodeId", "description": "Target <code>DOMNode</code> id." }, 90 { "name": "nodeId", "$ref": "NodeId", "optional": true, "description": "The target <code>DOMNode</code> id if the event listener is for a node." }, 91 { "name": "onWindow", "type": "boolean", "optional": true, "description": "True if the event listener was added to the window." }, 91 92 { "name": "location", "$ref": "Debugger.Location", "optional": true, "description": "Handler code location." }, 92 93 { "name": "handlerName", "type": "string", "optional": true, "description": "Event handler function name." }, 93 { "name": "handlerObject", "$ref": "Runtime.RemoteObject", "optional": true, "description": "Event handler function value." },94 94 { "name": "passive", "type": "boolean", "optional": true, "description": "<code>EventListener</code>'s passive." }, 95 95 { "name": "once", "type": "boolean", "optional": true, "description": "<code>EventListener</code>'s once." }, … … 290 290 "description": "Returns event listeners relevant to the node.", 291 291 "parameters": [ 292 { "name": "nodeId", "$ref": "NodeId", "description": "Id of the node to get listeners for." }, 293 { "name": "objectGroup", "type": "string", "optional": true, "description": "Symbolic group name for handler value. Handler value is not returned without this parameter specified." } 292 { "name": "nodeId", "$ref": "NodeId", "description": "Id of the node to get listeners for." } 294 293 ], 295 294 "returns": [ -
trunk/Source/WebCore/ChangeLog
r243243 r243244 1 2019-03-20 Devin Rousso <drousso@apple.com> 2 3 Web Inspector: DOM: include window as part of any event listener chain 4 https://bugs.webkit.org/show_bug.cgi?id=195730 5 <rdar://problem/48916872> 6 7 Reviewed by Timothy Hatcher. 8 9 Test: inspector/dom/getEventListenersForNode.html 10 11 * inspector/agents/InspectorDOMAgent.h: 12 (WebCore::EventListenerInfo::EventListenerInfo): Deleted. 13 * inspector/agents/InspectorDOMAgent.cpp: 14 (WebCore::InspectorDOMAgent::getEventListenersForNode): 15 (WebCore::InspectorDOMAgent::buildObjectForEventListener): 16 (WebCore::InspectorDOMAgent::getEventListeners): Deleted. 17 1 18 2019-03-20 Devin Rousso <drousso@apple.com> 2 19 -
trunk/Source/WebCore/inspector/agents/InspectorDOMAgent.cpp
r243207 r243244 877 877 } 878 878 879 void InspectorDOMAgent::getEventListenersForNode(ErrorString& errorString, int nodeId, const String* objectGroup,RefPtr<JSON::ArrayOf<Inspector::Protocol::DOM::EventListener>>& listenersArray)879 void InspectorDOMAgent::getEventListenersForNode(ErrorString& errorString, int nodeId, RefPtr<JSON::ArrayOf<Inspector::Protocol::DOM::EventListener>>& listenersArray) 880 880 { 881 881 listenersArray = JSON::ArrayOf<Inspector::Protocol::DOM::EventListener>::create(); 882 Node* node = assertNode(errorString, nodeId); 882 883 auto* node = assertNode(errorString, nodeId); 883 884 if (!node) 884 885 return; 886 887 Vector<RefPtr<EventTarget>> ancestors; 888 ancestors.append(node); 889 for (auto* ancestor = node->parentOrShadowHostNode(); ancestor; ancestor = ancestor->parentOrShadowHostNode()) 890 ancestors.append(ancestor); 891 if (auto* window = node->document().domWindow()) 892 ancestors.append(window); 893 894 struct EventListenerInfo { 895 RefPtr<EventTarget> eventTarget; 896 const AtomicString eventType; 897 const EventListenerVector eventListeners; 898 }; 899 885 900 Vector<EventListenerInfo> eventInformation; 886 getEventListeners(node, eventInformation, true); 901 for (size_t i = ancestors.size(); i; --i) { 902 auto& ancestor = ancestors[i - 1]; 903 for (auto& eventType : ancestor->eventTypes()) { 904 EventListenerVector filteredListeners; 905 for (auto& listener : ancestor->eventListeners(eventType)) { 906 if (listener->callback().type() == EventListener::JSEventListenerType) 907 filteredListeners.append(listener); 908 } 909 if (!filteredListeners.isEmpty()) 910 eventInformation.append({ ancestor, eventType, WTFMove(filteredListeners) }); 911 } 912 } 887 913 888 914 auto addListener = [&] (RegisteredEventListener& listener, const EventListenerInfo& info) { … … 892 918 893 919 for (auto& inspectorEventListener : m_eventListenerEntries.values()) { 894 if (inspectorEventListener.matches(*info. node, info.eventType, listener.callback(), listener.useCapture())) {920 if (inspectorEventListener.matches(*info.eventTarget, info.eventType, listener.callback(), listener.useCapture())) { 895 921 identifier = inspectorEventListener.identifier; 896 922 disabled = inspectorEventListener.disabled; … … 901 927 902 928 if (!identifier) { 903 InspectorEventListener inspectorEventListener(m_lastEventListenerId++, *info. node, info.eventType, listener.callback(), listener.useCapture());929 InspectorEventListener inspectorEventListener(m_lastEventListenerId++, *info.eventTarget, info.eventType, listener.callback(), listener.useCapture()); 904 930 905 931 identifier = inspectorEventListener.identifier; … … 910 936 } 911 937 912 listenersArray->addItem(buildObjectForEventListener(listener, identifier, info.eventType, info.node, objectGroup, disabled, hasBreakpoint));938 listenersArray->addItem(buildObjectForEventListener(listener, identifier, *info.eventTarget, info.eventType, disabled, hasBreakpoint)); 913 939 }; 914 940 … … 916 942 size_t eventInformationLength = eventInformation.size(); 917 943 for (auto& info : eventInformation) { 918 for (auto& listener : info.eventListener Vector) {944 for (auto& listener : info.eventListeners) { 919 945 if (listener->useCapture()) 920 946 addListener(*listener, info); … … 925 951 for (size_t i = eventInformationLength; i; --i) { 926 952 const EventListenerInfo& info = eventInformation[i - 1]; 927 for (auto& listener : info.eventListener Vector) {953 for (auto& listener : info.eventListeners) { 928 954 if (!listener->useCapture()) 929 955 addListener(*listener, info); 930 }931 }932 }933 934 void InspectorDOMAgent::getEventListeners(Node* node, Vector<EventListenerInfo>& eventInformation, bool includeAncestors)935 {936 // The Node's Ancestors including self.937 Vector<Node*> ancestors;938 // Push this node as the firs element.939 ancestors.append(node);940 if (includeAncestors) {941 for (ContainerNode* ancestor = node->parentOrShadowHostNode(); ancestor; ancestor = ancestor->parentOrShadowHostNode())942 ancestors.append(ancestor);943 }944 945 // Nodes and their Listeners for the concerned event types (order is top to bottom)946 for (size_t i = ancestors.size(); i; --i) {947 Node* ancestor = ancestors[i - 1];948 EventTargetData* d = ancestor->eventTargetData();949 if (!d)950 continue;951 // Get the list of event types this Node is concerned with952 for (auto& type : d->eventListenerMap.eventTypes()) {953 auto& listeners = ancestor->eventListeners(type);954 EventListenerVector filteredListeners;955 filteredListeners.reserveInitialCapacity(listeners.size());956 for (auto& listener : listeners) {957 if (listener->callback().type() == EventListener::JSEventListenerType)958 filteredListeners.uncheckedAppend(listener);959 }960 if (!filteredListeners.isEmpty())961 eventInformation.append(EventListenerInfo(ancestor, type, WTFMove(filteredListeners)));962 956 } 963 957 } … … 1661 1655 } 1662 1656 1663 Ref<Inspector::Protocol::DOM::EventListener> InspectorDOMAgent::buildObjectForEventListener(const RegisteredEventListener& registeredEventListener, int identifier, const AtomicString& eventType, Node* node, const String* objectGroupId, bool disabled, bool hasBreakpoint)1657 Ref<Inspector::Protocol::DOM::EventListener> InspectorDOMAgent::buildObjectForEventListener(const RegisteredEventListener& registeredEventListener, int identifier, EventTarget& eventTarget, const AtomicString& eventType, bool disabled, bool hasBreakpoint) 1664 1658 { 1665 1659 Ref<EventListener> eventListener = registeredEventListener.callback(); 1666 1660 1667 JSC::ExecState* exec = nullptr;1668 JSC::JSObject* handlerObject = nullptr;1669 JSC::JSFunction* handlerFunction = nullptr;1670 1661 String handlerName; 1671 1662 int lineNumber = 0; … … 1675 1666 auto& scriptListener = downcast<JSEventListener>(eventListener.get()); 1676 1667 1668 Document* document = nullptr; 1669 if (auto* scriptExecutionContext = eventTarget.scriptExecutionContext()) { 1670 if (is<Document>(scriptExecutionContext)) 1671 document = downcast<Document>(scriptExecutionContext); 1672 } else if (is<Node>(eventTarget)) 1673 document = &downcast<Node>(eventTarget).document(); 1674 1675 JSC::JSObject* handlerObject = nullptr; 1676 JSC::ExecState* exec = nullptr; 1677 1677 1678 JSC::JSLockHolder lock(scriptListener.isolatedWorld().vm()); 1678 1679 1679 exec = execStateFromNode(scriptListener.isolatedWorld(), &node->document()); 1680 handlerObject = scriptListener.jsFunction(node->document()); 1680 if (document) { 1681 handlerObject = scriptListener.jsFunction(*document); 1682 exec = execStateFromNode(scriptListener.isolatedWorld(), document); 1683 } 1684 1681 1685 if (handlerObject && exec) { 1682 handlerFunction = JSC::jsDynamicCast<JSC::JSFunction*>(exec->vm(), handlerObject);1686 JSC::JSFunction* handlerFunction = JSC::jsDynamicCast<JSC::JSFunction*>(exec->vm(), handlerObject); 1683 1687 1684 1688 if (!handlerFunction) { … … 1717 1721 .setUseCapture(registeredEventListener.useCapture()) 1718 1722 .setIsAttribute(eventListener->isAttribute()) 1719 .setNodeId(pushNodePathToFrontend(node))1720 1723 .release(); 1721 if (objectGroupId && handlerObject && exec) { 1722 InjectedScript injectedScript = m_injectedScriptManager.injectedScriptFor(exec); 1723 if (!injectedScript.hasNoValue()) 1724 value->setHandlerObject(injectedScript.wrapObject(handlerObject, *objectGroupId)); 1725 } 1724 if (is<Node>(eventTarget)) 1725 value->setNodeId(pushNodePathToFrontend(&downcast<Node>(eventTarget))); 1726 else if (is<DOMWindow>(eventTarget)) 1727 value->setOnWindow(true); 1726 1728 if (!scriptID.isNull()) { 1727 1729 auto location = Inspector::Protocol::Debugger::Location::create() -
trunk/Source/WebCore/inspector/agents/InspectorDOMAgent.h
r243207 r243244 78 78 typedef String ErrorString; 79 79 80 struct EventListenerInfo {81 EventListenerInfo(Node* node, const AtomicString& eventType, EventListenerVector&& eventListenerVector)82 : node(node)83 , eventType(eventType)84 , eventListenerVector(WTFMove(eventListenerVector))85 {86 }87 88 Node* node;89 const AtomicString eventType;90 const EventListenerVector eventListenerVector;91 };92 93 80 class InspectorDOMAgent final : public InspectorAgentBase, public Inspector::DOMBackendDispatcherHandler { 94 81 WTF_MAKE_NONCOPYABLE(InspectorDOMAgent); … … 130 117 void getDataBindingsForNode(ErrorString&, int nodeId, RefPtr<JSON::ArrayOf<Inspector::Protocol::DOM::DataBinding>>& dataArray) override; 131 118 void getAssociatedDataForNode(ErrorString&, int nodeId, Optional<String>& associatedData) override; 132 void getEventListenersForNode(ErrorString&, int nodeId, const WTF::String* objectGroup,RefPtr<JSON::ArrayOf<Inspector::Protocol::DOM::EventListener>>& listenersArray) override;119 void getEventListenersForNode(ErrorString&, int nodeId, RefPtr<JSON::ArrayOf<Inspector::Protocol::DOM::EventListener>>& listenersArray) override; 133 120 void setEventListenerDisabled(ErrorString&, int eventListenerId, bool disabled) override; 134 121 void setBreakpointForEventListener(ErrorString&, int eventListenerId) override; … … 157 144 void setInspectedNode(ErrorString&, int nodeId) override; 158 145 159 void getEventListeners(Node*, Vector<EventListenerInfo>& listenersArray, bool includeAncestors);160 161 162 146 // InspectorInstrumentation 163 147 int identifierForNode(Node&); … … 249 233 Ref<JSON::ArrayOf<Inspector::Protocol::DOM::Node>> buildArrayForContainerChildren(Node* container, int depth, NodeToIdMap* nodesMap); 250 234 RefPtr<JSON::ArrayOf<Inspector::Protocol::DOM::Node>> buildArrayForPseudoElements(const Element&, NodeToIdMap* nodesMap); 251 Ref<Inspector::Protocol::DOM::EventListener> buildObjectForEventListener(const RegisteredEventListener&, int identifier, const AtomicString& eventType, Node*, const String* objectGroupId, bool disabled, bool hasBreakpoint);235 Ref<Inspector::Protocol::DOM::EventListener> buildObjectForEventListener(const RegisteredEventListener&, int identifier, EventTarget&, const AtomicString& eventType, bool disabled, bool hasBreakpoint); 252 236 RefPtr<Inspector::Protocol::DOM::AccessibilityProperties> buildObjectForAccessibilityProperties(Node*); 253 237 void processAccessibilityChildren(AccessibilityObject&, JSON::ArrayOf<int>&); -
trunk/Source/WebInspectorUI/ChangeLog
r243242 r243244 1 2019-03-20 Devin Rousso <drousso@apple.com> 2 3 Web Inspector: DOM: include window as part of any event listener chain 4 https://bugs.webkit.org/show_bug.cgi?id=195730 5 <rdar://problem/48916872> 6 7 Reviewed by Timothy Hatcher. 8 9 Allow non-nodes (e.g. `window`) to be listed as the target of an event listener. 10 Add support for the same concept when showing breakpoint details after pausing on a specific 11 event listener in the Debugger/Sources navigation sidebar. 12 13 * UserInterface/Views/DOMNodeDetailsSidebarPanel.js: 14 (WI.DOMNodeDetailsSidebarPanel.prototype.initialLayout): 15 (WI.DOMNodeDetailsSidebarPanel.prototype._refreshEventListeners.generateGroupsByEvent): 16 (WI.DOMNodeDetailsSidebarPanel.prototype._refreshEventListeners.generateGroupsByTarget): Added. 17 (WI.DOMNodeDetailsSidebarPanel.prototype._refreshEventListeners.eventListenersCallback): 18 (WI.DOMNodeDetailsSidebarPanel.prototype._refreshEventListeners): 19 (WI.DOMNodeDetailsSidebarPanel.prototype._refreshEventListeners.generateGroupsByNode): Deleted. 20 21 * UserInterface/Views/EventListenerSectionGroup.js: 22 (WI.EventListenerSectionGroup.prototype._targetTextOrLink): Added. 23 (WI.EventListenerSectionGroup.prototype._nodeTextOrLink): Deleted. 24 25 * UserInterface/Views/DebuggerSidebarPanel.js: 26 (WI.DebuggerSidebarPanel.prototype._addBreakpoint): 27 (WI.DebuggerSidebarPanel.prototype._breakpointTreeOutlineDeleteTreeElement): 28 (WI.DebuggerSidebarPanel.prototype._treeSelectionDidChange): 29 (WI.DebuggerSidebarPanel.prototype._updatePauseReasonSection): 30 * UserInterface/Views/DebuggerSidebarPanel.css: 31 (.sidebar > .panel.navigation.debugger > .content > .breakpoints .tree-outline .item.event-target-window .icon): Added. 32 33 * UserInterface/Views/SourcesNavigationSidebarPanel.js: 34 (WI.SourcesNavigationSidebarPanel): 35 (WI.SourcesNavigationSidebarPanel.prototype._addBreakpoint): 36 (WI.SourcesNavigationSidebarPanel.prototype._updatePauseReasonSection): 37 (WI.SourcesNavigationSidebarPanel.prototype._handleTreeSelectionDidChange): 38 * UserInterface/Views/SourcesNavigationSidebarPanel.css: 39 (.sidebar > .panel.navigation.sources > .content > .breakpoints .tree-outline .item.event-target-window .icon): Added. 40 41 * Localizations/en.lproj/localizedStrings.js: 42 1 43 2019-03-20 Devin Rousso <drousso@apple.com> 2 44 -
trunk/Source/WebInspectorUI/Localizations/en.lproj/localizedStrings.js
r243220 r243244 516 516 localizedStrings["Group Media Requests"] = "Group Media Requests"; 517 517 localizedStrings["Group by Event"] = "Group by Event"; 518 localizedStrings["Group by Node"] = "Group by Node";519 518 localizedStrings["Group by Path"] = "Group by Path"; 519 localizedStrings["Group by Target"] = "Group by Target"; 520 520 localizedStrings["Group by Type"] = "Group by Type"; 521 521 localizedStrings["Grouping Method"] = "Grouping Method"; … … 1029 1029 localizedStrings["Tag"] = "Tag"; 1030 1030 localizedStrings["Take snapshot"] = "Take snapshot"; 1031 localizedStrings["Target"] = "Target"; 1031 1032 localizedStrings["Template Content"] = "Template Content"; 1032 1033 localizedStrings["Text"] = "Text"; -
trunk/Source/WebInspectorUI/UserInterface/Views/DOMNodeDetailsSidebarPanel.js
r242820 r243244 91 91 92 92 createOption(WI.UIString("Group by Event"), WI.DOMNodeDetailsSidebarPanel.EventListenerGroupingMethod.Event); 93 createOption(WI.UIString("Group by Node"), WI.DOMNodeDetailsSidebarPanel.EventListenerGroupingMethod.Node);93 createOption(WI.UIString("Group by Target"), WI.DOMNodeDetailsSidebarPanel.EventListenerGroupingMethod.Target); 94 94 95 95 eventListenersGroupMethodSelectElement.value = this._eventListenerGroupingMethodSetting.value; … … 342 342 return; 343 343 344 const windowTargetIdentifier = Symbol("window"); 345 344 346 function createEventListenerSection(title, eventListeners, options = {}) { 345 347 let groups = eventListeners.map((eventListener) => new WI.EventListenerSectionGroup(eventListener, options)); … … 355 357 let eventListenerTypes = new Map; 356 358 for (let eventListener of eventListeners) { 357 eventListener.node = WI.domManager.nodeForId(eventListener.nodeId); 359 console.assert(eventListener.nodeId || eventListener.onWindow); 360 if (eventListener.nodeId) 361 eventListener.node = WI.domManager.nodeForId(eventListener.nodeId); 358 362 359 363 let eventListenersForType = eventListenerTypes.get(eventListener.type); 360 364 if (!eventListenersForType) 361 365 eventListenerTypes.set(eventListener.type, eventListenersForType = []); 362 363 366 eventListenersForType.push(eventListener); 364 367 } … … 374 377 } 375 378 376 function generateGroupsBy Node(eventListeners) {377 let eventListener Nodes = new Map;379 function generateGroupsByTarget(eventListeners) { 380 let eventListenerTargets = new Map; 378 381 for (let eventListener of eventListeners) { 379 eventListener.node = WI.domManager.nodeForId(eventListener.nodeId); 380 381 let eventListenersForNode = eventListenerNodes.get(eventListener.node); 382 if (!eventListenersForNode) 383 eventListenerNodes.set(eventListener.node, eventListenersForNode = []); 384 385 eventListenersForNode.push(eventListener); 382 console.assert(eventListener.nodeId || eventListener.onWindow); 383 if (eventListener.nodeId) 384 eventListener.node = WI.domManager.nodeForId(eventListener.nodeId); 385 386 let target = eventListener.onWindow ? windowTargetIdentifier : eventListener.node; 387 let eventListenersForTarget = eventListenerTargets.get(target); 388 if (!eventListenersForTarget) 389 eventListenerTargets.set(target, eventListenersForTarget = []); 390 eventListenersForTarget.push(eventListener); 386 391 } 387 392 388 393 let rows = []; 394 395 function generateSectionForTarget(target) { 396 let eventListenersForTarget = eventListenerTargets.get(target); 397 if (!eventListenersForTarget) 398 return; 399 400 eventListenersForTarget.sort((a, b) => a.type.toLowerCase().extendedLocaleCompare(b.type.toLowerCase())); 401 402 let title = target === windowTargetIdentifier ? WI.unlocalizedString("window") : target.displayName; 403 404 let section = createEventListenerSection(title, eventListenersForTarget, {hideTarget: true}); 405 if (target instanceof WI.DOMNode) 406 WI.bindInteractionsForNodeToElement(target, section.titleElement, {ignoreClick: true}); 407 rows.push(section); 408 } 389 409 390 410 let currentNode = domNode; 391 411 do { 392 let eventListenersForNode = eventListenerNodes.get(currentNode); 393 if (!eventListenersForNode) 394 continue; 395 396 eventListenersForNode.sort((a, b) => a.type.toLowerCase().extendedLocaleCompare(b.type.toLowerCase())); 397 398 let section = createEventListenerSection(currentNode.displayName, eventListenersForNode, {hideNode: true}); 399 WI.bindInteractionsForNodeToElement(currentNode, section.titleElement, {ignoreClick: true}); 400 rows.push(section); 412 generateSectionForTarget(currentNode); 401 413 } while (currentNode = currentNode.parentNode); 414 415 generateSectionForTarget(windowTargetIdentifier); 402 416 403 417 return rows; … … 425 439 break; 426 440 427 case WI.DOMNodeDetailsSidebarPanel.EventListenerGroupingMethod. Node:428 this._eventListenersSectionGroup.rows = generateGroupsBy Node.call(this, eventListeners);441 case WI.DOMNodeDetailsSidebarPanel.EventListenerGroupingMethod.Target: 442 this._eventListenersSectionGroup.rows = generateGroupsByTarget.call(this, eventListeners); 429 443 break; 430 444 } … … 951 965 WI.DOMNodeDetailsSidebarPanel.EventListenerGroupingMethod = { 952 966 Event: "event", 953 Node: "node",967 Target: "target", 954 968 }; -
trunk/Source/WebInspectorUI/UserInterface/Views/DebuggerSidebarPanel.css
r242768 r243244 104 104 } 105 105 106 .sidebar > .panel.navigation.debugger > .content > .breakpoints .tree-outline .item.event-target-window .icon { 107 content: url(../Images/TypeObject.svg); 108 } 109 106 110 @media (prefers-color-scheme: dark) { 107 111 .sidebar > .panel.navigation.debugger .warning-banner { -
trunk/Source/WebInspectorUI/UserInterface/Views/DebuggerSidebarPanel.js
r242937 r243244 495 495 constructor = WI.EventBreakpointTreeElement; 496 496 497 if (breakpoint.eventListener) 498 parentTreeElement = getDOMNodeTreeElement(breakpoint.eventListener.node); 497 if (breakpoint.eventListener) { 498 let eventTargetTreeElement = null; 499 if (breakpoint.eventListener.onWindow) { 500 if (!DebuggerSidebarPanel.__windowEventTargetRepresentedObject) 501 DebuggerSidebarPanel.__windowEventTargetRepresentedObject = {__window: true}; 502 503 eventTargetTreeElement = this._breakpointsContentTreeOutline.findTreeElement(DebuggerSidebarPanel.__windowEventTargetRepresentedObject); 504 if (!eventTargetTreeElement) { 505 const subtitle = null; 506 eventTargetTreeElement = new WI.GeneralTreeElement(["event-target-window"], WI.unlocalizedString("window"), subtitle, DebuggerSidebarPanel.__windowEventTargetRepresentedObject); 507 this._addTreeElement(eventTargetTreeElement, parentTreeElement); 508 } 509 } else if (breakpoint.eventListener.node) 510 eventTargetTreeElement = getDOMNodeTreeElement(breakpoint.eventListener.node); 511 if (eventTargetTreeElement) 512 parentTreeElement = eventTargetTreeElement; 513 } 499 514 } else if (breakpoint instanceof WI.URLBreakpoint) { 500 515 constructor = WI.URLBreakpointTreeElement; … … 900 915 { 901 916 console.assert(treeElement.selected); 917 918 if (treeElement.representedObject === DebuggerSidebarPanel.__windowEventTargetRepresentedObject) { 919 let eventBreakpointsOnWindow = WI.domManager.eventListenerBreakpoints.filter((eventBreakpoint) => eventBreakpoint.eventListener.onWindow); 920 for (let eventBreakpoint of eventBreakpointsOnWindow) 921 WI.domManager.removeBreakpointForEventListener(eventBreakpoint.eventListener); 922 return true; 923 } 924 902 925 console.assert(treeElement instanceof WI.ResourceTreeElement || treeElement instanceof WI.ScriptTreeElement); 903 926 if (!(treeElement instanceof WI.ResourceTreeElement) && !(treeElement instanceof WI.ScriptTreeElement)) … … 954 977 || treeElement instanceof WI.EventBreakpointTreeElement 955 978 || treeElement instanceof WI.URLBreakpointTreeElement) 979 return; 980 981 if (treeElement.representedObject === DebuggerSidebarPanel.__windowEventTargetRepresentedObject) 956 982 return; 957 983 … … 1232 1258 console.assert(eventListener.eventListenerId === pauseData.eventListenerId); 1233 1259 1234 let ownerElementRow = new WI.DetailsSectionSimpleRow(WI.UIString("Element"), WI.linkifyNodeReference(eventListener.node)); 1235 rows.push(ownerElementRow); 1260 let value = null; 1261 if (eventListener.onWindow) 1262 value = WI.unlocalizedString("window"); 1263 else if (eventListener.node) 1264 value = WI.linkifyNodeReference(eventListener.node); 1265 if (value) 1266 rows.push(new WI.DetailsSectionSimpleRow(WI.UIString("Target"), value)); 1236 1267 } 1237 1268 -
trunk/Source/WebInspectorUI/UserInterface/Views/EventListenerSectionGroup.js
r241110 r243244 35 35 if (!options.hideType) 36 36 rows.push(new WI.DetailsSectionSimpleRow(WI.UIString("Event"), this._eventListener.type)); 37 if (!options.hide Node)38 rows.push(new WI.DetailsSectionSimpleRow(WI.UIString(" Node"), this._nodeTextOrLink()));37 if (!options.hideTarget) 38 rows.push(new WI.DetailsSectionSimpleRow(WI.UIString("Target"), this._targetTextOrLink())); 39 39 rows.push(new WI.DetailsSectionSimpleRow(WI.UIString("Function"), this._functionTextOrLink())); 40 40 … … 66 66 // Private 67 67 68 _ nodeTextOrLink()68 _targetTextOrLink() 69 69 { 70 var node = this._eventListener.node; 71 console.assert(node); 72 if (!node) 73 return ""; 70 if (this._eventListener.onWindow) 71 return WI.unlocalizedString("window"); 74 72 75 if (node.nodeType() === Node.DOCUMENT_NODE) 76 return "document"; 73 let node = this._eventListener.node; 74 if (node) 75 return WI.linkifyNodeReference(node); 77 76 78 return WI.linkifyNodeReference(node); 77 console.assert(); 78 return ""; 79 79 } 80 80 -
trunk/Source/WebInspectorUI/UserInterface/Views/SourcesNavigationSidebarPanel.css
r243225 r243244 142 142 } 143 143 144 .sidebar > .panel.navigation.sources > .content > .breakpoints .tree-outline .item.event-target-window .icon { 145 content: url(../Images/TypeObject.svg); 146 } 147 144 148 @media (prefers-dark-interface) { 145 149 .sidebar > .panel.navigation.sources > .content > .warning-banner { -
trunk/Source/WebInspectorUI/UserInterface/Views/SourcesNavigationSidebarPanel.js
r243225 r243244 143 143 this._breakpointsTreeOutline.ondelete = (treeElement) => { 144 144 console.assert(treeElement.selected); 145 146 if (treeElement.representedObject === SourcesNavigationSidebarPanel.__windowEventTargetRepresentedObject) { 147 let eventBreakpointsOnWindow = WI.domManager.eventListenerBreakpoints.filter((eventBreakpoint) => eventBreakpoint.eventListener.onWindow); 148 for (let eventBreakpoint of eventBreakpointsOnWindow) 149 WI.domManager.removeBreakpointForEventListener(eventBreakpoint.eventListener); 150 return true; 151 } 152 145 153 console.assert(treeElement instanceof WI.ResourceTreeElement || treeElement instanceof WI.ScriptTreeElement); 146 154 if (!(treeElement instanceof WI.ResourceTreeElement) && !(treeElement instanceof WI.ScriptTreeElement)) … … 902 910 constructor = WI.EventBreakpointTreeElement; 903 911 904 if (breakpoint.eventListener) 905 parentTreeElement = getDOMNodeTreeElement(breakpoint.eventListener.node); 912 if (breakpoint.eventListener) { 913 let eventTargetTreeElement = null; 914 if (breakpoint.eventListener.onWindow) { 915 if (!SourcesNavigationSidebarPanel.__windowEventTargetRepresentedObject) 916 SourcesNavigationSidebarPanel.__windowEventTargetRepresentedObject = {__window: true}; 917 918 eventTargetTreeElement = this._breakpointsTreeOutline.findTreeElement(SourcesNavigationSidebarPanel.__windowEventTargetRepresentedObject); 919 if (!eventTargetTreeElement) { 920 const subtitle = null; 921 eventTargetTreeElement = new WI.GeneralTreeElement(["event-target-window"], WI.unlocalizedString("window"), subtitle, SourcesNavigationSidebarPanel.__windowEventTargetRepresentedObject); 922 this._insertDebuggerTreeElement(eventTargetTreeElement, parentTreeElement); 923 } 924 } else if (breakpoint.eventListener.node) 925 eventTargetTreeElement = getDOMNodeTreeElement(breakpoint.eventListener.node); 926 if (eventTargetTreeElement) 927 parentTreeElement = eventTargetTreeElement; 928 } 906 929 } else if (breakpoint instanceof WI.URLBreakpoint) { 907 930 constructor = WI.URLBreakpointTreeElement; … … 1256 1279 console.assert(eventListener.eventListenerId === pauseData.eventListenerId); 1257 1280 1258 let ownerElementRow = new WI.DetailsSectionSimpleRow(WI.UIString("Element"), WI.linkifyNodeReference(eventListener.node)); 1259 rows.push(ownerElementRow); 1281 let value = null; 1282 if (eventListener.onWindow) 1283 value = WI.unlocalizedString("window"); 1284 else if (eventListener.node) 1285 value = WI.linkifyNodeReference(eventListener.node); 1286 if (value) 1287 rows.push(new WI.DetailsSectionSimpleRow(WI.UIString("Target"), value)); 1260 1288 } 1261 1289 … … 1387 1415 || treeElement instanceof WI.EventBreakpointTreeElement 1388 1416 || treeElement instanceof WI.URLBreakpointTreeElement) 1417 return; 1418 1419 if (treeElement.representedObject === SourcesNavigationSidebarPanel.__windowEventTargetRepresentedObject) 1389 1420 return; 1390 1421
Note: See TracChangeset
for help on using the changeset viewer.