--- a/devtools/client/shared/components/reps/event.js
+++ b/devtools/client/shared/components/reps/event.js
@@ -19,51 +19,71 @@ define(function (require, exports, modul
*/
let Event = React.createClass({
displayName: "event",
propTypes: {
object: React.PropTypes.object.isRequired
},
+ getTitle: function (props) {
+ let preview = props.object.preview;
+ let title = preview.type;
+
+ if (preview.eventKind == "key" && preview.modifiers && preview.modifiers.length) {
+ title = `${title} ${preview.modifiers.join("-")}`;
+ }
+ return title;
+ },
+
render: function () {
// Use `Object.assign` to keep `this.props` without changes because:
// 1. JSON.stringify/JSON.parse is slow.
// 2. Immutable.js is planned for the future.
- let props = Object.assign({}, this.props);
+ let props = Object.assign({
+ title: this.getTitle(this.props)
+ }, this.props);
props.object = Object.assign({}, this.props.object);
props.object.preview = Object.assign({}, this.props.object.preview);
- props.object.preview.ownProperties = props.object.preview.properties;
+
+ props.object.preview.ownProperties = {};
+ if (props.object.preview.target) {
+ Object.assign(props.object.preview.ownProperties, {
+ target: props.object.preview.target
+ });
+ }
+ Object.assign(props.object.preview.ownProperties, props.object.preview.properties);
+
delete props.object.preview.properties;
props.object.ownPropertyLength =
Object.keys(props.object.preview.ownProperties).length;
switch (props.object.class) {
case "MouseEvent":
props.isInterestingProp = (type, value, name) => {
- return (name == "clientX" ||
- name == "clientY" ||
- name == "layerX" ||
- name == "layerY");
+ return ["target", "clientX", "clientY", "layerX", "layerY"].includes(name);
};
break;
case "KeyboardEvent":
props.isInterestingProp = (type, value, name) => {
- return (name == "key" ||
- name == "charCode" ||
- name == "keyCode");
+ return ["target", "key", "charCode", "keyCode"].includes(name);
};
break;
case "MessageEvent":
props.isInterestingProp = (type, value, name) => {
- return (name == "isTrusted" ||
- name == "data");
+ return ["target", "isTrusted", "data"].includes(name);
};
break;
+ default:
+ props.isInterestingProp = (type, value, name) => {
+ // We want to show the properties in the order they are declared.
+ return Object.keys(props.object.preview.ownProperties).includes(name);
+ };
}
+
return rep(props);
}
});
// Registration
function supportsObject(grip, type) {
if (!isGrip(grip)) {
--- a/devtools/client/shared/components/test/mochitest/test_reps_event.html
+++ b/devtools/client/shared/components/test/mochitest/test_reps_event.html
@@ -14,58 +14,148 @@ Test Event rep
</head>
<body>
<pre id="test">
<script src="head.js" type="application/javascript;version=1.8"></script>
<script type="application/javascript;version=1.8">
window.onload = Task.async(function* () {
let { Rep } = browserRequire("devtools/client/shared/components/reps/rep");
let { Event } = browserRequire("devtools/client/shared/components/reps/event");
+ const { MODE } = browserRequire("devtools/client/shared/components/reps/constants");
try {
// Test that correct rep is chosen
const renderedRep = shallowRenderComponent(Rep, { object: getGripStub("testEvent") });
is(renderedRep.type, Event.rep, `Rep correctly selects ${Event.rep.displayName}`);
yield testEvent();
yield testMouseEvent();
yield testKeyboardEvent();
+ yield testKeyboardEventWithModifiers();
yield testMessageEvent();
+
+ yield testOnMouseOver();
+ yield testOnMouseOut();
} catch(e) {
ok(false, "Got an error: " + DevToolsUtils.safeErrorString(e));
} finally {
SimpleTest.finish();
}
function testEvent() {
- const renderedComponent = renderComponent(Event.rep, { object: getGripStub("testEvent") });
+ const renderedComponent = renderComponent(Event.rep, {
+ object: getGripStub("testEvent"),
+ });
is(renderedComponent.textContent,
- "Event { isTrusted: true, eventPhase: 2, bubbles: false, 7 more… }",
- "Event rep has expected text content for an event");
+ "beforeprint { target: http://example.com, isTrusted: true, " +
+ "currentTarget: http://example.com, 8 more… }",
+ "Event rep has expected text content for an event");
}
function testMouseEvent() {
- const renderedComponent = renderComponent(Event.rep, { object: getGripStub("testMouseEvent") });
+ const renderedComponent = renderComponent(Event.rep, {
+ object: getGripStub("testMouseEvent")
+ });
is(renderedComponent.textContent,
- "MouseEvent { clientX: 62, clientY: 18, layerX: 0, 2 more… }",
- "Event rep has expected text content for a mouse event");
+ "click { target: div#test, clientX: 62, clientY: 18, 3 more… }",
+ "Event rep has expected text content for a mouse event");
+
+ const longRenderedComponent = renderComponent(Event.rep, {
+ object: getGripStub("testMouseEvent"),
+ mode: MODE.LONG,
+ });
+ is(longRenderedComponent.textContent,
+ "click { target: div#test, buttons: 0, clientX: 62, clientY: 18, layerX: 0, " +
+ "layerY: 0 }",
+ "Event rep has expected text content for a mouse event in long mode");
}
function testKeyboardEvent() {
- const renderedComponent = renderComponent(Event.rep, { object: getGripStub("testKeyboardEvent") });
+ const renderedComponent = renderComponent(Event.rep, {
+ object: getGripStub("testKeyboardEvent")
+ });
is(renderedComponent.textContent,
- "KeyboardEvent { key: \"Control\", charCode: 0, keyCode: 17 }",
+ "keyup { target: body, key: \"Control\", charCode: 0, 1 more… }",
"Event rep has expected text content for a keyboard event");
+
+ const longRenderedComponent = renderComponent(Event.rep, {
+ object: getGripStub("testKeyboardEvent"),
+ mode: MODE.LONG,
+ });
+ is(longRenderedComponent.textContent,
+ `keyup { target: body, key: "Control", charCode: 0, keyCode: 17 }`,
+ "Event rep has expected text content for a keyboard event in long mode");
+ }
+
+ function testKeyboardEventWithModifiers() {
+ const renderedComponent = renderComponent(Event.rep, {
+ object: getGripStub("testKeyboardEventWithModifiers"),
+ mode: MODE.LONG,
+ });
+
+ is(renderedComponent.textContent,
+ `keyup Meta-Shift { target: body, key: "M", charCode: 0, keyCode: 77 }`,
+ "Event rep has expected text content for a keyboard event with modifiers " +
+ "in long mode");
}
function testMessageEvent() {
- const renderedComponent = renderComponent(Event.rep, { object: getGripStub("testMessageEvent") });
+ const renderedComponent = renderComponent(Event.rep, {
+ object: getGripStub("testMessageEvent")
+ });
is(renderedComponent.textContent,
- "MessageEvent { isTrusted: false, data: \"test data\", origin: \"null\", 7 more… }",
+ `message { target: http://example.com, isTrusted: false, data: "test data", ` +
+ "8 more… }",
"Event rep has expected text content for a message event");
+
+ const longRenderedComponent = renderComponent(Event.rep, {
+ object: getGripStub("testMessageEvent"),
+ mode: MODE.LONG,
+ });
+ is(longRenderedComponent.textContent,
+ `message { target: http://example.com, isTrusted: false, data: "test data", ` +
+ `origin: "null", lastEventId: "", source: , ports: message, currentTarget: , ` +
+ `eventPhase: 2, bubbles: false, 1 more… }`,
+ "Event rep has expected text content for a message event in long mode");
+ }
+
+ function testOnMouseOver() {
+ const stub = getGripStub("testMouseEvent");
+
+ let mouseOverValue;
+ let onDOMNodeMouseOver = (object) => {
+ mouseOverValue = object;
+ };
+ const renderedComponent = renderComponent(Event.rep, {
+ object: stub, onDOMNodeMouseOver
+ });
+
+ const node = renderedComponent.querySelector(".objectBox-node");
+ TestUtils.Simulate.mouseOver(node);
+
+ is(mouseOverValue, stub.preview.target, "onDOMNodeMouseOver is called with " +
+ "the expected argument when mouseover is fired on the Rep");
+ }
+
+ function testOnMouseOut() {
+ const stub = getGripStub("testMouseEvent");
+
+ let called = false;
+ let onDOMNodeMouseOut = (object) => {
+ called = true;
+ };
+ const renderedComponent = renderComponent(Event.rep, {
+ object: stub,
+ onDOMNodeMouseOut
+ });
+
+ const node = renderedComponent.querySelector(".objectBox-node");
+ TestUtils.Simulate.mouseOut(node);
+
+ is(called, true, "onDOMNodeMouseOut is called when mouseout is fired on the Rep");
}
function getGripStub(name) {
switch (name) {
case "testEvent":
return {
"type": "object",
"class": "Event",
@@ -214,16 +304,54 @@ window.onload = Task.async(function* ()
"attributesLength": 0
}
},
"eventKind": "key",
"modifiers": []
}
};
+ case "testKeyboardEventWithModifiers":
+ return {
+ "type": "object",
+ "class": "KeyboardEvent",
+ "actor": "server1.conn21.obj49",
+ "extensible": true,
+ "frozen": false,
+ "sealed": false,
+ "ownPropertyLength": 1,
+ "preview": {
+ "kind": "DOMEvent",
+ "type": "keyup",
+ "properties": {
+ "key": "M",
+ "charCode": 0,
+ "keyCode": 77
+ },
+ "target": {
+ "type": "object",
+ "class": "HTMLBodyElement",
+ "actor": "server1.conn21.obj50",
+ "extensible": true,
+ "frozen": false,
+ "sealed": false,
+ "ownPropertyLength": 0,
+ "preview": {
+ "kind": "DOMNode",
+ "nodeType": 1,
+ "nodeName": "body",
+ "attributes": {},
+ "attributesLength": 0
+ }
+ },
+ "eventKind": "key",
+ "modifiers": ["Meta", "Shift"]
+ }
+ };
+
case "testMessageEvent":
return {
"type": "object",
"class": "MessageEvent",
"actor": "server1.conn3.obj34",
"extensible": true,
"frozen": false,
"sealed": false,
@@ -280,17 +408,17 @@ window.onload = Task.async(function* ()
"class": "Window",
"actor": "server1.conn3.obj35",
"extensible": true,
"frozen": false,
"sealed": false,
"ownPropertyLength": 760,
"preview": {
"kind": "ObjectWithURL",
- "url": ""
+ "url": "http://example.com"
}
}
}
};
}
}
});