Skip to content

Commit ebd4be5

Browse files
committed
New Example: MessageManager
1 parent 2d2a9b3 commit ebd4be5

File tree

9 files changed

+265
-0
lines changed

9 files changed

+265
-0
lines changed

MessageManager/README.md

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
Message Manager
2+
===============
3+
An example extension showing how to communicate between a chrome scope
4+
(extension) and content scope (panel ifreame with type="content")
5+
6+
Instructions
7+
------------
8+
1. Install the extension
9+
2. Open developer tools toolbox (F12 or Menu -> Developer -> Toogle Tools)
10+
3. See the `My Panel` panel
11+
12+
Further Resources
13+
-----------------
14+
* Add-on SDK: https://developer.mozilla.org/en-US/Add-ons/SDK
15+
* DevTools API: https://developer.mozilla.org/en-US/docs/Tools/DevToolsAPI
16+
* Coding Style: https://github.com/mozilla/addon-sdk/wiki/Coding-style-guide
17+
* DevTools Extension Examples: https://github.com/firebug/devtools-extension-examples
18+
* DevTools/Hacking: https://wiki.mozilla.org/DevTools/Hacking

MessageManager/data/frame-script.js

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
/* See license.txt for terms of usage */
2+
3+
"use strict";
4+
5+
(function({content, addMessageListener, sendAsyncMessage, removeMessageListener}) {
6+
7+
const document = content.document;
8+
const window = content;
9+
10+
/**
11+
* Listener for message from the inspector panel (chrome scope).
12+
*/
13+
function messageListener(message) {
14+
const { type, data } = message.data;
15+
16+
console.log("Message from chrome: " + data);
17+
};
18+
19+
addMessageListener("message/from/chrome", messageListener);
20+
21+
/**
22+
* Clean up
23+
*/
24+
window.addEventListener("unload", event => {
25+
removeMessageListener("message/from/chrome", messageListener);
26+
})
27+
28+
/**
29+
* Send a message back to the parent panel (chrome scope).
30+
*/
31+
function postChromeMessage(type, data) {
32+
sendAsyncMessage("message/from/content", {
33+
type: type,
34+
data: data,
35+
});
36+
}
37+
38+
/**
39+
* TEST: Send a test message to the chrome scope when
40+
* the user clicks within the frame.
41+
*/
42+
window.addEventListener("click", event => {
43+
postChromeMessage("click", "Hello from content scope!");
44+
})
45+
46+
})(this);

MessageManager/data/icon-16.png

1.62 KB
Loading

MessageManager/data/myPanel.html

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
<!DOCTYPE html>
2+
<html>
3+
<head>
4+
<meta charset="utf-8"/>
5+
</head>
6+
<style type="text/css">
7+
body {
8+
background-color: white;
9+
}
10+
</style>
11+
<body>
12+
<h1>Hello World!</h1>
13+
</body>
14+
</html>

MessageManager/lib/main.js

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
/* See license.txt for terms of usage */
2+
3+
"use strict";
4+
5+
const { MyExtension } = require("./myExtension.js");
6+
const { MyPanel } = require("./myPanel.js");
7+
8+
/**
9+
* Application entry point. Read MDN to learn more about Add-on SDK:
10+
* https://developer.mozilla.org/en-US/Add-ons/SDK
11+
*/
12+
function main(options, callbacks) {
13+
// Initialize extension object (singleton).
14+
MyExtension.initialize(options);
15+
}
16+
17+
function onUnload(reason) {
18+
MyExtension.shutdown(reason);
19+
}
20+
21+
// Exports from this module
22+
exports.main = main;
23+
exports.onUnload = onUnload;

MessageManager/lib/myExtension.js

Lines changed: 57 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,57 @@
1+
/* See license.txt for terms of usage */
2+
3+
"use strict";
4+
5+
const { Cu } = require("chrome");
6+
7+
const { gDevTools } = Cu.import("resource:///modules/devtools/gDevTools.jsm", {});
8+
9+
/**
10+
* This object represents the extension. It's a singleton (only one
11+
* instance created).
12+
*/
13+
const MyExtension =
14+
/** @lends MyExtension */
15+
{
16+
initialize: function(options) {
17+
// Hook developer tools events.
18+
gDevTools.on("toolbox-ready", this.onToolboxReady);
19+
gDevTools.on("toolbox-destroy", this.onToolboxDestroy);
20+
gDevTools.on("toolbox-destroyed", this.onToolboxClosed);
21+
},
22+
23+
shutdown: function(reason) {
24+
gDevTools.off("toolbox-ready", this.onToolboxReady);
25+
gDevTools.off("toolbox-destroy", this.onToolboxDestroy);
26+
gDevTools.off("toolbox-destroyed", this.onToolboxClosed);
27+
},
28+
29+
// Event Handlers
30+
31+
/**
32+
* Executed by the framework when {@Toolbox} is opened and ready to use.
33+
* There is one instance of the {@Toolbox} per browser window.
34+
* The event is fired after the current panel is opened & loaded
35+
* (happens asynchronously) and ready to use.
36+
*/
37+
onToolboxReady: function(event, toolbox) {
38+
},
39+
40+
/**
41+
* Executed by the framework at the beginning of the {@Toolbox} destroy
42+
* process. All instantiated panel objects are still available, which
43+
* makes this method suitable for e.g. removing event listeners.
44+
*/
45+
onToolboxDestroy: function(eventId, target) {
46+
},
47+
48+
/**
49+
* Executed by the framework at the end of the {@Toolbox} destroy
50+
* process. All panel objects are destroyed at this moment.
51+
*/
52+
onToolboxClosed: function(eventId, target) {
53+
},
54+
};
55+
56+
// Exports from this module
57+
exports.MyExtension = MyExtension;

MessageManager/lib/myPanel.js

Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
/* See license.txt for terms of usage */
2+
3+
"use strict";
4+
5+
const self = require("sdk/self");
6+
7+
const { Cu, Ci } = require("chrome");
8+
const { Panel } = require("dev/panel.js");
9+
const { Class } = require("sdk/core/heritage");
10+
const { Tool } = require("dev/toolbox");
11+
const { viewFor } = require("sdk/view/core");
12+
13+
/**
14+
* This object represents a new {@Toolbox} panel
15+
*/
16+
const MyPanel = Class(
17+
/** @lends MyPanel */
18+
{
19+
extends: Panel,
20+
21+
label: "My Panel",
22+
tooltip: "My panel tooltip",
23+
icon: "./icon-16.png",
24+
url: "./myPanel.html",
25+
26+
/**
27+
* Executed by the framework when an instance of this panel is created.
28+
* There is one instance of this panel per {@Toolbox}. The panel is
29+
* instantiated when selected in the toolbox for the first time.
30+
*/
31+
initialize: function(options) {
32+
this.onMessage = this.onMessage.bind(this);
33+
},
34+
35+
/**
36+
* Executed by the framework when the panel is destroyed.
37+
*/
38+
dispose: function() {
39+
},
40+
41+
/**
42+
* Executed by the framework when the panel content frame is
43+
* ready (document state == interactive).
44+
*/
45+
onReady: function() {
46+
this.panelFrame = viewFor(this);
47+
48+
// Get frame's message manager. Read more about message managers on MDN:
49+
// https://developer.mozilla.org/en-US/Firefox/Multiprocess_Firefox/The_message_manager
50+
const { messageManager } = this.panelFrame.frameLoader;
51+
messageManager.addMessageListener("message/from/content",
52+
this.onMessage);
53+
54+
// Load frame script with content API for receiving
55+
// and sending messages.
56+
let url = self.data.url("frame-script.js");
57+
messageManager.loadFrameScript(url, false);
58+
59+
// Send test message to the content
60+
this.postContentMessage("<message-id>", "Hello from chrome scope!");
61+
},
62+
63+
// Chrome <-> Content Communication
64+
65+
onMessage: function(message) {
66+
const { type, data } = message.data;
67+
68+
console.log("Message from content: " + data);
69+
},
70+
71+
postContentMessage: function(type, data) {
72+
let { messageManager } = this.panelFrame.frameLoader;
73+
messageManager.sendAsyncMessage("message/from/chrome", {
74+
type: type,
75+
data: data,
76+
});
77+
},
78+
});
79+
80+
const myTool = new Tool({
81+
name: "MyTool",
82+
panels: {
83+
myPanel: MyPanel
84+
}
85+
});

MessageManager/package.json

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
{
2+
"name": "messagemanager",
3+
"title": "MessageManager",
4+
5+
"description": "How to send messages between chrome and content scope",
6+
"author": "Jan Odvarko",
7+
"license": "New BSD",
8+
"version": "0.1.0",
9+
"main": "lib/main"
10+
}

MessageManager/test/test-main.js

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
var main = require("./main");
2+
3+
exports["test main"] = function(assert) {
4+
assert.pass("Unit test running!");
5+
};
6+
7+
exports["test main async"] = function(assert, done) {
8+
assert.pass("async Unit test running!");
9+
done();
10+
};
11+
12+
require("sdk/test").run(exports);

0 commit comments

Comments
 (0)