Copyright © 2005 J.C. Wesdorp
May 30, 2005
Abstract
This document show how to create and register a sidebar for the Firefox browser.
Table of Contents
This article descripes how to create a registered sidebar for the Firefox browser.
This article is a quick start for the creation of a new sidebar for Firefox. What we will do is creating a sidebar and register it so it will be availible in the menu. The goal is creating an empty sidebar that can be used as start for new sidebar applications.
Creating a sidebar requires some GUI creation and registration in the destination application. First a simple XUL page is created. Then the registration files are made and finally the sidebar is packed into an installable XPI file.
This article is a quick start, it won't explain all elements of XUL, packaging and XPI's. It's preferable you have some basic knowledge of how XUL works and how Firefox handles extensions.
Additions to Firefox are installed with packages. A packages exists of the XUL and application logics. Optionally locales and skins can be included. Most additions are provided with a default tree structure, although not required it is recommended to use this structure. Here the package for the sidebar is created, the files included are listed below.
Create all folders, except for skin. It is not used
for this tutorial.
The locale holds the locale, only the en-US locale
is created. It is listed in Example 2. The locale includes the name and shortcut
keys for the sidebar.
Example 2. chrome/locale/en-US/emptysidebar.dtd"
<!ENTITY emptysidebar.title "EmptySidebar"> <!ENTITY openEmptySidebar.commandkey "E"> <!ENTITY openEmptySidebar.modifierskey "shift accel">
The content folder includes our sidebar, the emptysidebar.xul is
printed in Example 3.
It creates a page
holding one label. Other elements can be included, please read the XUL
tutorials for more information.
Example 3. chrome/content/emptysidebar.xul
<?xml version="1.0"?> <?xml-stylesheet href="chrome://global/skin/" type"text/css" ?> <?xml-stylesheet href="chrome://browser/skin/browser.css" type="text/css" ?> <!DOCTYPE page SYSTEM "chrome://emptysidebar/locale/emptysidebar.dtd"> <page id="sbEmptySidebar" title="&emptysidebar.title;" xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul" > <vbox flex="1"> <label id="atest" value="&emptysidebar.title;" /> </vbox> </page>
New extensions can be registered in the menus or popups, Firefox uses an overlays for extending menus. This is an separate XUL file that specifies the location of menu items. The sidebar here is added to the View | Sidebar menu. The overlay file is listed in Example 4.
Example 4. chrome/contents/emptysidebar-overlay.xul
<?xml version="1.0"?>
<!DOCTYPE overlay SYSTEM "chrome://emptysidebar/locale/emptysidebar.dtd">
<overlay id="emptySidebarOverlay"
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
<menupopup id="viewSidebarMenu">
<menuitem key="key_openEmptySidebar" observes="viewEmptySidebar" />
</menupopup>
<keyset id="mainKeyset">
<key id="key_openEmptySidebar" command="viewEmptySidebar"
key="&openEmptySidebar.commandkey;"
modifiers="&openEmptySidebar.modifierskey;" />
</keyset>
<broadcasterset id="mainBroadcasterSet">
<broadcaster id="viewEmptySidebar"
label="&emptysidebar.title;"
autoCheck="false"
type="checkbox"
group="sidebar"
sidebarurl="chrome://emptysidebar/content/emptysidebar.xul"
sidebarTitle="&emptysidebar.title;"
oncommand="toggleSidebar('viewEmptySidebar');" />
</broadcasterset>
</overlay>
The overlay file consists of three entries, the menu definition, shortcut keys
and the event handler for UI elements. The broadcaster is linked to an UI
element with the observes attribute. The broadcaster
viewEmptySidebar defines how a click on the menu is handled
or the shortcut keys are pressed.
Finally, the contents file are created. We create a contents.rdf
for the folders content and locale/en-US
folder. The files are listed in Example 5 and Example 6.
Example 5. chrome/content/contents.rdf
<?xml version="1.0"?> <RDF:RDF xmlns:RDF="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:chrome="http://www.mozilla.org/rdf/chrome#"> <!-- list all packages --> <RDF:Seq about="urn:mozilla:package:root"> <RDF:li resource="urn:mozilla:package:emptysidebar"/> </RDF:Seq> <!-- package information --> <RDF:Description about="urn:mozilla:package:emptysidebar" chrome:displayName="emptysidebar" chrome:author="www.occidopagus.nl" chrome:authorURL="http://www.occidopagus.nl" chrome:name="emptysidebar" chrome:extension="true" chrome:description="An example project" > </RDF:Description> <!-- Overlay information --> <RDF:Seq about="urn:mozilla:overlays"> <RDF:li resource="chrome://browser/content/browser.xul" /> </RDF:Seq> <RDF:Seq about="chrome://browser/content/browser.xul"> <RDF:li>chrome://emptysidebar/content/emptysidebar-overlay.xul</RDF:li> </RDF:Seq> </RDF:RDF>
Example 6. chrome/locale/en-US/contents.rdf
<?xml version="1.0"?> <RDF:RDF xmlns:RDF="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:chrome="http://www.mozilla.org/rdf/chrome#"> <RDF:Seq about="urn:mozilla:locale:root"> <RDF:li resource="urn:mozilla:locale:en-US" /> </RDF:Seq> <RDF:Description about="urn:mozilla:locale:en-US"> <chrome:packages> <RDF:Seq about="urn:mozilla:locale:en-US:packages"> <RDF:li resource="urn:mozilla:locale:en-US:emptysidebar" /> </RDF:Seq> </chrome:packages> </RDF:Description> </RDF:RDF>
Now that all files have been created the extension can be installed in
Firefox. All installed packages are listed in the chrome.rdf
but this file should not be changed manually. For developers the easiest way is using the
installed-chrome.txt file for registration. When Firefox
is started it reads this file to find out which packages are installed, if new
packages are found they are added to the chrome.rdf file.
The installed-chrome.txt can be found in the
Firefox chrome folder. Copy the emptysidebar
folder to this folder and add the lines listed in Example 7 to installed-chrome.txt.
Example 7. installed-chrome.txt
content,install,url,resource:/chrome/emptysidebar/content/ locale,install,url,resource:/chrome/emptysidebar/locale/en-US/
Restart Firefox and the sidebar is included in the menu.
Now that we have a sidebar it is time to make it availible to the world.
Installation requires the creation of an XPI file which is identified as
extension in Firefox. The XPI is a ZIP file containing the content and locale
files, an install script named install.js and a manifest
called install.rdf.
Example 8. chrome/install.js
const APP_NAME = "emptySidebar";
const CHROME_NAME = "emptysidebar";
const APP_VERSION = "1.0";
const APP_FILE = "emptysidebar.jar";
const APP_CONTENT_PATH = "content/";
initInstall(APP_NAME, APP_CHROME_NAME, APP_VERSION);
var chromeFolder = getFolder("Current User", "chrome");
setPackageFilder(chromFolder);
addFile(APP_NAME, "chrome/" + APP_FILE, chromeFolder, "");
var jarFoder = getFolder(chromeFolder, APP_FILE);
registerChrome(CONTENT | PROFILE_CHROME, jarFolder, APP_CONTENT_PATH);
var result = getLastError();
if (result == SUCCESS) {
performInstall();
} else {
cancelInstall(result);
}
Example 9. emptysidebar/install.rdf
<?xml version="1.0"?>
<!-- install.rdf template copied from http://kb.mozillazine.org/Install.rdf -->
<RDF xmlns="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:em="http://www.mozilla.org/2004/em-rdf#">
<Description about="urn:mozilla:install-manifest">
<em:id>{3B1B83AA-D06E-11D9-AF35-000D932E38A8}</em:id>
<em:name>EmptySidebar Extension</em:name>
<em:version>1.0</em:version>
<em:description>Example extension for creation and registration of a sidebar.</em:description>
<em:creator>J.C. Wesdorp</em:creator>
<!-- optional items -->
<em:homepageURL>http://occidopagus.nl/firefox/emptysidebar/</em:homepageURL>
<!-- Firefox -->
<em:targetApplication>
<Description>
<em:id>{ec8030f7-c20a-464f-9b0e-13a3a9e97384}</em:id>
<em:minVersion>0.9</em:minVersion>
<em:maxVersion>1.0</em:maxVersion>
</Description>
</em:targetApplication>
<!-- This is not needed for Firefox 1.1 and later. Only include this
if you want to make your extension compatible with older versions -->
<em:file>
<Description about="urn:mozilla:extension:file:emptysidebar.jar">
<em:package>content/</em:package>
<!-- optional items -->
<em:locale>locale/en-US/</em:locale>
</Description>
</em:file>
</Description>
</RDF>
Each extension is identified by a GUID code. A GUID has to be created for each extension. Tools for GUID creation are GuidGen from Microsoft or uuidgen on Unix systems.
The content and locale files are packed into emptysidebar.jar,
create this file in the chrome folder. On unix systems:
~/src/emptysidebar$cd chrome~/src/emptysidebar/chrome$zip -r emptysidebar.jar content/ locale/
Finally, create the XPI file. This is an ZIP file containing the JAR file and the install scripts.
~/src/emptysidebar/chrome$cd ..~/src/emptysidebar$zip emptysidebar.xpi install.* chrome/emptysidebar.jar
Open Firefox and browse to the folder containing emptysidebar.xpi.
Click on the file and the Extension installation window pops up. After a restart of Firefox the
sidebar is installed. Or click here
for the XPI.
Creating Applications with Mozilla
http://books.mozdev.org/html/index.html
Packaging Firefox/Thunderbird Extensions
http://www.bengoodger.com/software/mb/extensions/packaging/extensions.html
Mozillazine: Setting up extension development environment
http://kb.mozillazine.org/Setting_up_extension_development_environment
Mozillazine: Install.rdf
http://kb.mozillazine.org/Install.rdf