Merge from cvs-trunk-mirror to mozilla-central.

--HG--
rename : js/src/js.c => js/src/js.cpp
rename : js/src/jsfun.c => js/src/jsfun.cpp
rename : js/src/jsinterp.c => js/src/jsinterp.cpp
rename : js/src/jsobj.c => js/src/jsobj.cpp
This commit is contained in:
jorendorff@mozilla.com 2007-10-31 10:40:29 -05:00
Родитель 0a4915ceb4 ad25b4ed1d
Коммит df571c0233
581 изменённых файлов: 18015 добавлений и 5853 удалений

Просмотреть файл

@ -1639,15 +1639,14 @@ nsresult nsAccessible::AppendFlatStringFromContentNode(nsIContent *aContent, nsA
nsresult nsAccessible::AppendFlatStringFromSubtree(nsIContent *aContent, nsAString *aFlatString)
{
static nsIContent *startContent = nsnull;
// never run into the same content node, to prevent infinite recursion
if (startContent == aContent) {
static PRBool isAlreadyHere; // Prevent recursion which can cause infinite loops
if (isAlreadyHere) {
return NS_OK;
}
if (!startContent) {
startContent = aContent;
}
isAlreadyHere = PR_TRUE;
nsresult rv = AppendFlatStringFromSubtreeRecurse(aContent, aFlatString);
isAlreadyHere = PR_FALSE;
if (NS_SUCCEEDED(rv) && !aFlatString->IsEmpty()) {
nsAString::const_iterator start, end;
aFlatString->BeginReading(start);
@ -1661,10 +1660,6 @@ nsresult nsAccessible::AppendFlatStringFromSubtree(nsIContent *aContent, nsAStri
aFlatString->Truncate(aFlatString->Length() - spacesToTruncate);
}
if (startContent == aContent) {
// we are leaving the original invoking
startContent = nsnull;
}
return rv;
}

Просмотреть файл

@ -64,7 +64,7 @@ public:
NS_IMETHOD GetChildCount(PRInt32 *_retval);
NS_IMETHOD GetAllowsAnonChildAccessibles(PRBool *aAllowsAnonChildren);
NS_IMETHOD GetChildAtPoint(PRInt32 aX, PRInt32 aY, nsIAccessible **aAccessible)
{ *aAccessible = this; return NS_OK; } // Don't walk into these
{ NS_ENSURE_ARG_POINTER(aAccessible); NS_ADDREF(*aAccessible = this); return NS_OK; } // Don't walk into these
};
/**

Просмотреть файл

@ -731,7 +731,7 @@ nsresult nsRootAccessible::HandleEventWithTarget(nsIDOMEvent* aEvent,
else
#endif
if (eventType.EqualsLiteral("focus")) {
if (aTargetNode == mDOMNode) {
if (aTargetNode == mDOMNode && mDOMNode != gLastFocusedNode) {
// Got focus event for the window, we will make sure that an accessible
// focus event for initial focus is fired. We do this on a short timer
// because the initial focus may not have been set yet.
@ -847,8 +847,15 @@ nsresult nsRootAccessible::HandleEventWithTarget(nsIDOMEvent* aEvent,
NS_ENSURE_TRUE(containerAccessible, NS_ERROR_FAILURE);
// It is not top level menuitem
// Only fire focus event if it is not inside collapsed popup
if (State(containerAccessible) & nsIAccessibleStates::STATE_COLLAPSED)
return NS_OK;
// and not a listitem of a combo box
if (State(containerAccessible) & nsIAccessibleStates::STATE_COLLAPSED) {
nsCOMPtr<nsIAccessible> containerParent;
containerAccessible->GetParent(getter_AddRefs(containerParent));
NS_ENSURE_TRUE(containerParent, NS_ERROR_FAILURE);
if (Role(containerParent) != nsIAccessibleRole::ROLE_COMBOBOX) {
return NS_OK;
}
}
}
}
nsAccEvent::PrepareForEvent(aTargetNode, PR_TRUE); // Always asynch, always from user input

Просмотреть файл

@ -57,7 +57,7 @@ public:
NS_IMETHOD GetDescription(nsAString& _retval);
NS_IMETHOD GetBounds(PRInt32 *x, PRInt32 *y, PRInt32 *width, PRInt32 *height);
NS_IMETHOD GetChildAtPoint(PRInt32 aX, PRInt32 aY, nsIAccessible **aAccessible)
{ *aAccessible = this; return NS_OK; } // Don't walk into these
{ NS_ENSURE_ARG_POINTER(aAccessible); NS_ADDREF(*aAccessible = this); return NS_OK; } // Don't walk into these
};
#endif

Просмотреть файл

@ -849,7 +849,10 @@ nsHTMLTableAccessible::GetTableLayout(nsITableLayout **aLayoutObject)
nsCOMPtr<nsIContent> content(do_QueryInterface(tableNode));
NS_ENSURE_TRUE(content, NS_ERROR_FAILURE);
nsIPresShell *presShell = content->GetDocument()->GetPrimaryShell();
nsIDocument *doc = content->GetDocument();
NS_ENSURE_TRUE(doc, NS_ERROR_FAILURE);
nsIPresShell *presShell = doc->GetPrimaryShell();
nsCOMPtr<nsISupports> layoutObject;
rv = presShell->GetLayoutObjectFor(content, getter_AddRefs(layoutObject));

Просмотреть файл

@ -200,8 +200,6 @@ pref("browser.urlbar.doubleClickSelectsAll", false);
#endif
pref("browser.urlbar.autoFill", false);
pref("browser.urlbar.matchOnlyTyped", false);
pref("browser.urlbar.hideProtocols", "");
pref("browser.urlbar.animateBlend", true);
pref("browser.download.useDownloadDir", true);
pref("browser.download.folderList", 0);
@ -380,7 +378,7 @@ pref("mousewheel.withmetakey.action",0);
pref("mousewheel.withmetakey.sysnumlines",true);
pref("mousewheel.withmetakey.numlines",1);
#endif
pref("mousewheel.withcontrolkey.action",3);
pref("mousewheel.withcontrolkey.action",5);
pref("mousewheel.withcontrolkey.sysnumlines",false);
pref("mousewheel.withcontrolkey.numlines",1);
@ -443,11 +441,7 @@ pref("browser.preferences.instantApply", false);
#else
pref("browser.preferences.instantApply", true);
#endif
#ifdef XP_MACOSX
pref("browser.preferences.animateFadeIn", true);
#else
pref("browser.preferences.animateFadeIn", false);
#endif
pref("browser.download.show_plugins_in_list", true);
pref("browser.download.hide_plugins_without_extensions", true);
@ -545,6 +539,10 @@ pref("browser.safebrowsing.provider.0.reportPhishURL", "http://{moz:locale}.phis
// FAQ URL
pref("browser.safebrowsing.warning.infoURL", "http://%LOCALE%.www.mozilla.com/%LOCALE%/firefox/phishing-protection/");
// Name of the about: page contributed by safebrowsing to handle display of error
// pages on phishing/malware hits. (bug 399233)
pref("urlclassifier.alternate_error_page", "blocked");
#endif
// defaults to true
@ -574,8 +572,5 @@ pref("accessibility.blockautorefresh", false);
// import bookmarks.html into Places bookmarks
pref("browser.places.importBookmarksHTML", true);
// Show infobar on chromeless windows
pref("browser.warn_chromeless_window.infobar", false);
// if false, will add the "Places" folder to the personal toolbar
pref("browser.places.createdDefaultQueries", false);

Просмотреть файл

@ -1,5 +1,8 @@
#aboutDialog {
padding: 0px 0px 10px 0px;
padding-top: 0;
-moz-padding-end: 0;
padding-bottom: 10px;
-moz-padding-start: 0;
width: 299px;
}
@ -20,53 +23,71 @@
}
#userAgent {
margin: 11px 20px 0px 13px;
margin-top: 11px;
-moz-margin-end: 20px;
margin-bottom: 0;
-moz-margin-start: 13px;
background-color: #FFFFFF;
color: #000000;
padding: 1px 0px 0px 3px;
padding-top: 1px;
-moz-padding-end: 0;
padding-bottom: 0;
-moz-padding-start: 3px;
-moz-appearance: none;
overflow: hidden;
border: 0px;
border: 0;
}
#groove {
margin-top: 0px;
margin-top: 0;
}
#creditsIframe {
cursor: default;
-moz-user-select: none;
border: 0px;
border: 0;
}
#version {
font-weight: bold;
color: #909090;
margin: 1em 0px 10px 17px;
margin-top: 1em;
-moz-margin-end: 0;
margin-bottom: 10px;
-moz-margin-start: 17px;
}
#distribution {
font-weight: bold;
color: #909090;
display: none;
margin: 0em 0px 0px 17px;
margin-top: 0;
-moz-margin-end: 0;
margin-bottom: 0;
-moz-margin-start: 17px;
}
#distributionId {
font-weight: bold;
color: #909090;
display: none;
margin: 0em 0px 10px 17px;
margin-top: 0;
-moz-margin-end: 0;
margin-bottom: 10px;
-moz-margin-start: 17px;
}
#copyright {
margin: 0px 0px 3px 16px;
margin-top: 0;
-moz-margin-end: 0;
margin-bottom: 3px;
-moz-margin-start: 16px;
}
button[dlgtype="extra2"] {
margin-left: 13px;
-moz-margin-start: 13px;
}
button[dlgtype="accept"] {
margin-right: 13px;
-moz-margin-end: 13px;
}

Просмотреть файл

@ -171,15 +171,15 @@
#endif
<menuitem label="&reloadCmd.label;" accesskey="&reloadCmd.accesskey;" command="Browser:Reload" key="key_reload"/>
<menuseparator/>
<menu id="viewTextZoomMenu" label="&textSize.label;" accesskey="&textSize.accesskey;" observes="isImage">
<menupopup>
<menuitem key="key_textZoomEnlarge" label="&textZoomEnlargeCmd.label;" accesskey="&textZoomEnlargeCmd.accesskey;"
command="cmd_textZoomEnlarge"/>
<menuitem key="key_textZoomReduce" label="&textZoomReduceCmd.label;" accesskey="&textZoomReduceCmd.accesskey;"
command="cmd_textZoomReduce"/>
<menu id="viewFullZoomMenu" label="&fullZoom.label;" accesskey="&fullZoom.accesskey;" observes="isImage">
<menupopup>
<menuitem key="key_fullZoomEnlarge" label="&fullZoomEnlargeCmd.label;" accesskey="&fullZoomEnlargeCmd.accesskey;"
command="cmd_fullZoomEnlarge"/>
<menuitem key="key_fullZoomReduce" label="&fullZoomReduceCmd.label;" accesskey="&fullZoomReduceCmd.accesskey;"
command="cmd_fullZoomReduce"/>
<menuseparator/>
<menuitem key="key_textZoomReset" label="&textZoomResetCmd.label;" accesskey="&textZoomResetCmd.accesskey;"
command="cmd_textZoomReset"/>
<menuitem key="key_fullZoomReset" label="&fullZoomResetCmd.label;" accesskey="&fullZoomResetCmd.accesskey;"
command="cmd_fullZoomReset"/>
</menupopup>
</menu>
<menu id="pageStyleMenu" label="&pageStyleMenu.label;" accesskey="&pageStyleMenu.accesskey;" observes="isImage">

Просмотреть файл

@ -50,7 +50,11 @@ var PlacesCommandHook = {
// Edit-bookmark panel
get panel() {
return document.getElementById("editBookmarkPanel");
delete this.panel;
var element = document.getElementById("editBookmarkPanel");
element.addEventListener("popuphiding", this, false);
element.addEventListener("keypress", this, true);
return this.panel = element;
},
// list of command elements (by id) to disable when the panel is opened
@ -129,13 +133,15 @@ var PlacesCommandHook = {
this._overlayLoading = true;
document.loadOverlay("chrome://browser/content/places/editBookmarkOverlay.xul",
loadObserver);
this.panel.addEventListener("popuphiding", this, false);
},
_doShowEditBookmarkPanel:
function PCH__doShowEditBookmarkPanel(aItemId, aAnchorElement, aPosition) {
this.panel.addEventListener("keypress", this, true);
this._blockCommands(); // un-done in the popuphiding handler
// Consume dismiss clicks, see bug 400924
this.panel.popupBoxObject
.setConsumeRollupEvent(Ci.nsIPopupBoxObject.ROLLUP_CONSUME);
this.panel.openPopup(aAnchorElement, aPosition, -1, -1);
gEditItemOverlay.initPanel(aItemId,
@ -405,7 +411,7 @@ var BookmarksEventHandler = {
node.localName == "menupopup")) {
if (node.localName == "menupopup")
node.hidePopup();
node = node.parentNode;
}
}
@ -415,9 +421,9 @@ var BookmarksEventHandler = {
// separately.
var bookmarksBar = document.getElementById("bookmarksBarContent");
if (bookmarksBar._chevron.getAttribute("open") == "true")
bookmarksBar._chevron.firstChild.hidePopupAndChildPopups();
bookmarksBar._chevron.firstChild.hidePopup();
},
/**
* Handler for command event for an item in the bookmarks toolbar.
* Menus and submenus from the folder buttons bubble up to this handler.
@ -426,17 +432,12 @@ var BookmarksEventHandler = {
* DOMEvent for the command
*/
onCommand: function BM_onCommand(aEvent) {
// If this is the special "Open All in Tabs" menuitem,
// load all the menuitems in tabs.
var target = aEvent.originalTarget;
if (target.hasAttribute("siteURI"))
openUILink(target.getAttribute("siteURI"), aEvent);
// If this is a normal bookmark, just load the bookmark's URI.
else if (!target.hasAttribute("openInTabs"))
if (target.node) {
PlacesUtils.getViewForNode(target)
.controller
.openSelectedNodeWithEvent(aEvent);
}
},
/**
@ -456,7 +457,6 @@ var BookmarksEventHandler = {
// Add the "Open (Feed Name)" menuitem if it's a livemark with a siteURI.
var numNodes = 0;
var hasMultipleEntries = false;
var hasFeedHomePage = false;
var currentChild = target.firstChild;
while (currentChild) {
if (currentChild.localName == "menuitem" && currentChild.node)
@ -473,32 +473,35 @@ var BookmarksEventHandler = {
if (numNodes > 1)
hasMultipleEntries = true;
var button = target.parentNode;
if (button.getAttribute("livemark") == "true" &&
button.hasAttribute("siteURI"))
hasFeedHomePage = true;
var itemId = target._resultNode.itemId;
var siteURIString = "";
if (itemId != -1 && PlacesUtils.livemarks.isLivemark(itemId)) {
var siteURI = PlacesUtils.livemarks.getSiteURI(itemId);
if (siteURI)
siteURIString = siteURI.spec;
}
if (hasMultipleEntries || hasFeedHomePage) {
if (hasMultipleEntries || siteURIString) {
var separator = document.createElement("menuseparator");
target.appendChild(separator);
if (hasFeedHomePage) {
if (siteURIString) {
var openHomePage = document.createElement("menuitem");
openHomePage.setAttribute(
"siteURI", button.getAttribute("siteURI"));
openHomePage.setAttribute("siteURI", siteURIString);
openHomePage.setAttribute("oncommand",
"openUILink(this.getAttribute('siteURI'), event);");
openHomePage.setAttribute(
"label",
PlacesUtils.getFormattedString("menuOpenLivemarkOrigin.label",
[button.getAttribute("label")]));
[target.parentNode.getAttribute("label")]));
target.appendChild(openHomePage);
}
if (hasMultipleEntries) {
var openInTabs = document.createElement("menuitem");
openInTabs.setAttribute("openInTabs", "true");
openInTabs.setAttribute("onclick", "checkForMiddleClick(this, event)");
openInTabs.setAttribute("oncommand",
"PlacesUtils.openContainerNodeInTabs(this.parentNode.getResultNode(), event);");
"PlacesUtils.openContainerNodeInTabs(this.parentNode._resultNode, event);");
openInTabs.setAttribute("label",
gNavigatorBundle.getString("menuOpenAllInTabs.label"));
target.appendChild(openInTabs);
@ -703,19 +706,19 @@ var PlacesMenuDNDController = {
// Close the bookmarks menu
var bookmarksMenu = document.getElementById("bookmarksMenu");
bookmarksMenu.firstChild.hidePopupAndChildPopups();
bookmarksMenu.firstChild.hidePopup();
var bookmarksBar = document.getElementById("bookmarksBarContent");
if (bookmarksBar) {
// Close the overflow chevron menu and all its children
bookmarksBar._chevron.firstChild.hidePopupAndChildPopups();
bookmarksBar._chevron.firstChild.hidePopup();
// Close all popups on the bookmarks toolbar
var toolbarItems = bookmarksBar.childNodes;
for (var i = 0; i < toolbarItems.length; ++i) {
var item = toolbarItems[i]
if (this._isContainer(item))
item.firstChild.hidePopupAndChildPopups();
item.firstChild.hidePopup();
}
}
},

Просмотреть файл

@ -101,9 +101,9 @@
<command id="Browser:Stop" oncommand="BrowserStop();" disabled="true"/>
<command id="Browser:Reload" oncommand="if (event.shiftKey) BrowserReloadSkipCache(); else BrowserReload()" disabled="true"/>
<command id="Browser:ReloadSkipCache" oncommand="BrowserReloadSkipCache()" disabled="true"/>
<command id="cmd_textZoomReduce" oncommand="TextZoom.reduce()"/>
<command id="cmd_textZoomEnlarge" oncommand="TextZoom.enlarge()"/>
<command id="cmd_textZoomReset" oncommand="TextZoom.reset()"/>
<command id="cmd_fullZoomReduce" oncommand="FullZoom.reduce()"/>
<command id="cmd_fullZoomEnlarge" oncommand="FullZoom.enlarge()"/>
<command id="cmd_fullZoomReset" oncommand="FullZoom.reset()"/>
<command id="Browser:OpenLocation" oncommand="openLocation();"/>
<command id="Tools:Search" oncommand="BrowserSearch.webSearch();"/>
@ -286,10 +286,10 @@
#endif
command="viewHistorySidebar"/>
<key id="key_textZoomReduce" key="&textZoomReduceCmd.commandkey;" command="cmd_textZoomReduce" modifiers="accel"/>
<key id="key_textZoomEnlarge" key="&textZoomEnlargeCmd.commandkey;" command="cmd_textZoomEnlarge" modifiers="accel"/>
<key key="&textZoomEnlargeCmd.commandkey2;" command="cmd_textZoomEnlarge" modifiers="accel"/>
<key id="key_textZoomReset" key="&textZoomResetCmd.commandkey;" command="cmd_textZoomReset" modifiers="accel"/>
<key id="key_fullZoomReduce" key="&fullZoomReduceCmd.commandkey;" command="cmd_fullZoomReduce" modifiers="accel"/>
<key id="key_fullZoomEnlarge" key="&fullZoomEnlargeCmd.commandkey;" command="cmd_fullZoomEnlarge" modifiers="accel"/>
<key key="&fullZoomEnlargeCmd.commandkey2;" command="cmd_fullZoomEnlarge" modifiers="accel"/>
<key id="key_fullZoomReset" key="&fullZoomResetCmd.commandkey;" command="cmd_fullZoomReset" modifiers="accel"/>
<key id="key_switchTextDirection" key="&bidiSwitchTextDirectionItem.commandkey;" command="cmd_switchTextDirection" modifiers="accel,shift" />

Просмотреть файл

@ -21,6 +21,7 @@
*
* Contributor(s):
* Myk Melez <myk@mozilla.org>
* Dão Gottwald <dao@mozilla.com>
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
@ -41,58 +42,35 @@
// From nsMouseScrollEvent::kIsHorizontal
const MOUSE_SCROLL_IS_HORIZONTAL = 1 << 2;
// Not sure where this comes from. It's one of the possible values
// for the mousewheel.* preferences.
const MOUSE_SCROLL_TEXTSIZE = 3;
// One of the possible values for the mousewheel.* preferences.
// From nsEventStateManager.cpp.
const MOUSE_SCROLL_FULLZOOM = 5;
/**
* Controls the "text zoom" setting and its site-specific preferences.
* Controls the "full zoom" setting and its site-specific preferences.
*/
var TextZoom = {
var FullZoom = {
//**************************************************************************//
// Name & Values
// The name of the setting. Identifies the setting in the prefs database.
name: "browser.content.text-zoom",
name: "browser.content.full-zoom",
// The global value (if any) for the setting. Retrieved from the prefs
// database when this handler gets initialized, then updated as it changes.
// If there is no global value, then this should be undefined.
globalValue: undefined,
// From viewZoomOverlay.js
minValue: 1,
maxValue: 2000,
defaultValue: 100,
//**************************************************************************//
// Convenience Getters
__zoomManager: null,
get _zoomManager() {
if (!this.__zoomManager)
this.__zoomManager = ZoomManager.prototype.getInstance();
return this.__zoomManager;
},
// Content Pref Service
__cps: null,
get _cps() {
if (!this.__cps)
this.__cps = Cc["@mozilla.org/content-pref/service;1"].
getService(Ci.nsIContentPrefService);
return this.__cps;
},
// Pref Branch
__prefBranch: null,
get _prefBranch() {
if (!this.__prefBranch)
this.__prefBranch = Cc["@mozilla.org/preferences-service;1"].
getService(Ci.nsIPrefBranch);
return this.__prefBranch;
delete this._cps;
return this._cps = Cc["@mozilla.org/content-pref/service;1"].
getService(Ci.nsIContentPrefService);
},
@ -104,8 +82,8 @@ var TextZoom = {
Components.interfaces.nsIContentPrefObserver,
Components.interfaces.nsISupports],
QueryInterface: function TextZoom_QueryInterface(aIID) {
if (!this.interfaces.some( function(v) { return aIID.equals(v) } ))
QueryInterface: function (aIID) {
if (!this.interfaces.some(function (v) aIID.equals(v)))
throw Cr.NS_ERROR_NO_INTERFACE;
return this;
},
@ -114,7 +92,7 @@ var TextZoom = {
//**************************************************************************//
// Initialization & Destruction
init: function TextZoom_init() {
init: function () {
// Listen for scrollwheel events so we can save scrollwheel-based changes.
window.addEventListener("DOMMouseScroll", this, false);
@ -129,7 +107,7 @@ var TextZoom = {
this._applyPrefToSetting();
},
destroy: function TextZoom_destroy() {
destroy: function () {
ContentPrefSink.removeObserver(this.name, this);
this._cps.removeObserver(this.name, this);
window.removeEventListener("DOMMouseScroll", this, false);
@ -149,12 +127,15 @@ var TextZoom = {
// nsIDOMEventListener
handleEvent: function TextZoom_handleEvent(event) {
// The only events we handle are DOMMouseScroll events.
this._handleMouseScrolled(event);
handleEvent: function (event) {
switch (event.type) {
case "DOMMouseScroll":
this._handleMouseScrolled(event);
break;
}
},
_handleMouseScrolled: function TextZoom__handleMouseScrolled(event) {
_handleMouseScrolled: function (event) {
// Construct the "mousewheel action" pref key corresponding to this event.
// Based on nsEventStateManager::GetBasePrefKeyForMouseWheel.
var pref = "mousewheel";
@ -174,8 +155,12 @@ var TextZoom = {
pref += ".action";
// Don't do anything if this isn't a "change text size" scroll event.
if (this._getAppPref(pref, null) != MOUSE_SCROLL_TEXTSIZE)
// Don't do anything if this isn't a "zoom" scroll event.
var isZoomEvent = false;
try {
isZoomEvent = (gPrefService.getIntPref(pref) == MOUSE_SCROLL_FULLZOOM);
} catch (e) {}
if (!isZoomEvent)
return;
// XXX Lazily cache all the possible action prefs so we don't have to get
@ -185,12 +170,12 @@ var TextZoom = {
// We have to call _applySettingToPref in a timeout because we handle
// the event before the event state manager has a chance to apply the zoom
// during nsEventStateManager::PostHandleEvent.
window.setTimeout(function() { TextZoom._applySettingToPref() }, 0);
window.setTimeout(function (self) { self._applySettingToPref() }, 0, this);
},
// nsIContentPrefObserver
onContentPrefSet: function TextZoom_onContentPrefSet(aGroup, aName, aValue) {
onContentPrefSet: function (aGroup, aName, aValue) {
if (aGroup == this._cps.grouper.group(gBrowser.currentURI))
this._applyPrefToSetting(aValue);
else if (aGroup == null) {
@ -204,7 +189,7 @@ var TextZoom = {
}
},
onContentPrefRemoved: function TextZoom_onContentPrefRemoved(aGroup, aName) {
onContentPrefRemoved: function (aGroup, aName) {
if (aGroup == this._cps.grouper.group(gBrowser.currentURI))
this._applyPrefToSetting();
else if (aGroup == null) {
@ -220,7 +205,7 @@ var TextZoom = {
// ContentPrefSink observer
onLocationChanged: function TextZoom_onLocationChanged(aURI, aName, aValue) {
onLocationChanged: function (aURI, aName, aValue) {
this._applyPrefToSetting(aValue);
},
@ -228,35 +213,35 @@ var TextZoom = {
//**************************************************************************//
// Setting & Pref Manipulation
reduce: function TextZoom_reduce() {
this._zoomManager.reduce();
reduce: function () {
ZoomManager.reduce();
this._applySettingToPref();
},
enlarge: function TextZoom_enlarge() {
this._zoomManager.enlarge();
enlarge: function () {
ZoomManager.enlarge();
this._applySettingToPref();
},
reset: function TextZoom_reset() {
reset: function () {
if (typeof this.globalValue != "undefined")
this._zoomManager.textZoom = this.globalValue;
ZoomManager.fullZoom = this.globalValue;
else
this._zoomManager.reset();
ZoomManager.reset();
this._removePref();
},
/**
* Set the text zoom for the current tab.
* Set the zoom level for the current tab.
*
* Per DocumentViewerImpl::SetTextZoom in nsDocumentViewer.cpp, it looks
* Per DocumentViewerImpl::SetFullZoom in nsDocumentViewer.cpp, it looks
* like we can set the zoom to its current value without significant impact
* on performance, as the setting is only applied if it differs from the
* current setting.
*
* And perhaps we should always set the zoom even if it were to incur
* a performance penalty, since SetTextZoom claims that child documents
* a performance penalty, since SetFullZoom claims that child documents
* may have a different zoom under unusual circumstances, and it implies
* that those child zooms should get updated when the parent zoom gets set.
*
@ -264,26 +249,26 @@ var TextZoom = {
* We don't check first to see if the new value is the same as the current
* one.
**/
_applyPrefToSetting: function TextZoom__applyPrefToSetting(aValue) {
_applyPrefToSetting: function (aValue) {
// Bug 375918 means this will sometimes throw, so we catch it
// and don't do anything in those cases.
try {
if (typeof aValue != "undefined")
this._zoomManager.textZoom = this._ensureValid(aValue);
ZoomManager.fullZoom = this._ensureValid(aValue);
else if (typeof this.globalValue != "undefined")
this._zoomManager.textZoom = this.globalValue;
ZoomManager.fullZoom = this.globalValue;
else
this._zoomManager.reset();
ZoomManager.reset();
}
catch(ex) {}
},
_applySettingToPref: function TextZoom__applySettingToPref() {
var textZoom = this._zoomManager.textZoom;
this._cps.setPref(gBrowser.currentURI, this.name, textZoom);
_applySettingToPref: function () {
var fullZoom = ZoomManager.fullZoom;
this._cps.setPref(gBrowser.currentURI, this.name, fullZoom);
},
_removePref: function TextZoom__removePref() {
_removePref: function () {
this._cps.removePref(gBrowser.currentURI, this.name);
},
@ -291,41 +276,16 @@ var TextZoom = {
//**************************************************************************//
// Utilities
_ensureValid: function TextZoom__ensureValid(aValue) {
_ensureValid: function (aValue) {
if (isNaN(aValue))
return this.defaultValue;
return 1;
if (aValue < this.minValue)
return this.minValue;
if (aValue < ZoomManager.MIN)
return ZoomManager.MIN;
if (aValue > this.maxValue)
return this.maxValue;
if (aValue > ZoomManager.MAX)
return ZoomManager.MAX;
return aValue;
},
/**
* Get a value from a pref or a default value if the pref doesn't exist.
*
* @param aPrefName
* @param aDefaultValue
* @returns the pref's value or the default (if it is missing)
*/
_getAppPref: function TextZoom__getAppPref(aPrefName, aDefaultValue) {
try {
switch (this._prefBranch.getPrefType(aPrefName)) {
case this._prefBranch.PREF_STRING:
return this._prefBranch.getCharPref(aPrefName);
case this._prefBranch.PREF_BOOL:
return this._prefBranch.getBoolPref(aPrefName);
case this._prefBranch.PREF_INT:
return this._prefBranch.getIntPref(aPrefName);
}
}
catch (ex) { /* return the default value */ }
return aDefaultValue;
}
};

Просмотреть файл

@ -362,7 +362,7 @@ function initPlacesDefaultQueries() {
var recentlyCreatedBookmarksItem = bmsvc.insertBookmark(placesFolder,
IO.newURI("place:folder=" + bookmarksRoot + "&folder=" + unfiledRoot +
"&queryType=" + Ci.nsINavHistoryQueryOptions.QUERY_TYPE_BOOKMARKS +
"&sort=" +
"&sort=" +
Ci.nsINavHistoryQueryOptions.SORT_BY_DATEADDED_DESCENDING +
"&excludeItemIfParentHasAnnotation=livemark%2FfeedURI" +
"&maxResults=" + maxResults +
@ -372,15 +372,17 @@ function initPlacesDefaultQueries() {
var recentlyVisitedBookmarksItem = bmsvc.insertBookmark(placesFolder,
IO.newURI("place:folder=" + bookmarksRoot + "&folder=" + unfiledRoot +
"&queryType=" + Ci.nsINavHistoryQueryOptions.QUERY_TYPE_BOOKMARKS +
"&sort=" + Ci.nsINavHistoryQueryOptions.SORT_BY_DATE_DESCENDING +
"&sort=" + Ci.nsINavHistoryQueryOptions.SORT_BY_DATE_DESCENDING +
"&excludeItemIfParentHasAnnotation=livemark%2FfeedURI" +
"&minVisits=1&maxResults=" + maxResults),
defaultIndex, recentlyVisitedBookmarksTitle);
var mostVisitedBookmarksItem = bmsvc.insertBookmark(placesFolder,
IO.newURI("place:folder=" + bookmarksRoot + "&folder=" + unfiledRoot +
"&queryType=" + Ci.nsINavHistoryQueryOptions.QUERY_TYPE_BOOKMARKS +
"&sort=" +
Ci.nsINavHistoryQueryOptions.SORT_BY_VISITCOUNT_DESCENDING +
"&sort=" +
Ci.nsINavHistoryQueryOptions.SORT_BY_VISITCOUNT_DESCENDING +
"&excludeItemIfParentHasAnnotation=livemark%2FfeedURI" +
"&minVisits=1&maxResults=" + maxResults),
defaultIndex, mostVisitedBookmarksTitle);
@ -388,28 +390,28 @@ function initPlacesDefaultQueries() {
IO.newURI("place:folder=" + tagRoot +
"&group=" + Ci.nsINavHistoryQueryOptions.GROUP_BY_FOLDER +
"&queryType=" + Ci.nsINavHistoryQueryOptions.QUERY_TYPE_BOOKMARKS +
"&applyOptionsToContainers=1" +
"&sort=" +
Ci.nsINavHistoryQueryOptions.SORT_BY_DATEADDED_DESCENDING +
"&applyOptionsToContainers=1" +
"&sort=" +
Ci.nsINavHistoryQueryOptions.SORT_BY_DATEADDED_DESCENDING +
"&resolveNullBookmarkTitles=1" +
"&maxResults=" + maxResults),
defaultIndex, recentlyUsedTagsTitle);
var mostUsedTagsItem = bmsvc.insertBookmark(placesFolder,
IO.newURI("place:folder=" + tagRoot +
IO.newURI("place:folder=" + tagRoot +
"&group=" + Ci.nsINavHistoryQueryOptions.GROUP_BY_FOLDER +
"&queryType=" + Ci.nsINavHistoryQueryOptions.QUERY_TYPE_BOOKMARKS +
"&applyOptionsToContainers=1" +
"&sort=" + Ci.nsINavHistoryQueryOptions.SORT_BY_COUNT_DESCENDING +
"&sort=" + Ci.nsINavHistoryQueryOptions.SORT_BY_COUNT_DESCENDING +
"&resolveNullBookmarkTitles=1" +
"&maxResults=" + maxResults),
defaultIndex, mostUsedTagsTitle);
var mostVisitedSitesItem = bmsvc.insertBookmark(placesFolder,
IO.newURI("place:queryType=" +
IO.newURI("place:queryType=" +
Ci.nsINavHistoryQueryOptions.QUERY_TYPE_HISTORY +
"&sort=" +
Ci.nsINavHistoryQueryOptions.SORT_BY_VISITCOUNT_DESCENDING +
"&sort=" +
Ci.nsINavHistoryQueryOptions.SORT_BY_VISITCOUNT_DESCENDING +
"&maxResults=" + maxResults),
defaultIndex, mostVisitedSitesTitle);
}
@ -1164,7 +1166,7 @@ function delayedStartup()
// apply text zoom settings to tabs restored by the session restore service.
try {
ContentPrefSink.init();
TextZoom.init();
FullZoom.init();
}
catch(ex) {
Components.utils.reportError("Failed to init content pref service:\n" + ex);
@ -1202,16 +1204,12 @@ function delayedStartup()
// bookmark-all-tabs command
gBookmarkAllTabsHandler = new BookmarkAllTabsHandler();
// Prevent chrome-spoofing popups from forging our chrome, by adding a
// notification box entry in cases of chromeless popups.
checkForChromelessWindow();
}
function BrowserShutdown()
{
try {
TextZoom.destroy();
FullZoom.destroy();
ContentPrefSink.destroy();
}
catch(ex) {
@ -1288,7 +1286,7 @@ function nonBrowserWindowStartup()
var disabledItems = ['cmd_newNavigatorTab', 'Browser:SavePage', 'Browser:SendLink',
'cmd_pageSetup', 'cmd_print', 'cmd_find', 'cmd_findAgain', 'viewToolbarsMenu',
'cmd_toggleTaskbar', 'viewSidebarMenuMenu', 'Browser:Reload', 'Browser:ReloadSkipCache',
'viewTextZoomMenu', 'pageStyleMenu', 'charsetMenu', 'View:PageSource', 'View:FullScreen',
'viewFullZoomMenu', 'pageStyleMenu', 'charsetMenu', 'View:PageSource', 'View:FullScreen',
'viewHistorySidebar', 'Browser:AddBookmarkAs', 'View:PageInfo', 'Tasks:InspectPage'];
var element;
@ -2233,6 +2231,16 @@ function PageProxyClickHandler(aEvent)
return true;
}
function URLBarOnInput(evt)
{
gBrowser.userTypedValue = gURLBar.value;
// If the user is interacting with the url bar, get rid of the identity popup
var ih = getIdentityHandler();
if(ih._identityPopup)
ih._identityPopup.hidePopup();
}
function URLBarOnDragOver(evt)
{
nsDragAndDrop.dragOver(evt, urlbarObserver);
@ -3848,6 +3856,7 @@ nsBrowserStatusHandler.prototype =
this.securityButton.removeAttribute("label");
this.securityButton.setAttribute("tooltiptext", this._tooltipText);
getIdentityHandler().checkIdentity(this._state, this._host);
},
// simulate all change notifications after switching tabs
@ -3942,6 +3951,10 @@ nsBrowserAccess.prototype =
return null;
}
if (!gPrefService)
gPrefService = Components.classes["@mozilla.org/preferences-service;1"]
.getService(Components.interfaces.nsIPrefBranch2);
var loadflags = isExternal ?
Ci.nsIWebNavigation.LOAD_FLAGS_FROM_EXTERNAL :
Ci.nsIWebNavigation.LOAD_FLAGS_NONE;
@ -3977,6 +3990,8 @@ nsBrowserAccess.prototype =
newWindow.QueryInterface(Ci.nsIInterfaceRequestor)
.getInterface(Ci.nsIWebNavigation)
.loadURI(url, loadflags, referrer, null, null);
if (!loadInBackground && isExternal)
newWindow.focus();
} catch(e) {
}
break;
@ -5576,87 +5591,6 @@ BookmarkAllTabsHandler.prototype = {
}
};
/**
* Check the chromehidden attribute to see if the toolbar is hidden. If so,
* and if they haven't disabled the security.warn_chromeless_window.infobar
* pref, show an infobar notification informing them of what's going on. This
* helps fight chrome spoofing on popups. See bug 337344
*/
function checkForChromelessWindow() {
var prefs = Components.classes["@mozilla.org/preferences-service;1"]
.getService(Components.interfaces.nsIPrefBranch);
// true by default
if (!prefs.getBoolPref("browser.warn_chromeless_window.infobar"))
return;
if (document.documentElement.getAttribute("chromehidden").indexOf("toolbar") != -1 ||
document.documentElement.getAttribute("chromehidden").indexOf("location") != -1) {
var bundle_browser = document.getElementById("bundle_browser");
// It's possible that something in the window.content.opener.location.path
// chain might be null. Rather than chaining a ton of 99% pass null checks,
// though, let's try/catch in order to fail gracefully
try {
var messageString = bundle_browser.getFormattedString("chromelessWindow.warningMessage",
[window.content.opener.location.host]);
} catch (ex) {
// An exception here is not worth breaking our security warning, but is worth
// logging, since it shouldn't happen.
Components.utils.reportError(ex);
messageString = bundle_browser.getString("chromelessWindow.warningNoLocation");
}
var notificationBox = gBrowser.getNotificationBox();
var notificationName = "chromeless-info";
if (notificationBox.getNotificationWithValue(notificationName)) {
Components.utils.reportError("Already have a chromeless-info notification!")
return;
}
var buttons = [{
label: bundle_browser.getString("chromelessWindow.showToolbarsButton"),
accessKey: bundle_browser.getString("chromelessWindow.accessKey"),
popup: null,
callback: function() { return showToolbars(); }
}];
notificationBox.appendNotification(messageString,
notificationName,
"chrome://browser/skin/Info.png",
notificationBox.PRIORITY_INFO_HIGH,
buttons);
}
}
/**
* Callback for "Show Toolbars" button in chromeless window notification box.
* Resets visibility of the go button stack and url bar, and wipes the
* chromehidden document attribute.
*/
function showToolbars() {
// Unhide the chrome elements
document.documentElement.removeAttribute("chromehidden");
// Undo the URLBar tweaks performed when the url bar was chromehidden
if (gURLBar) {
gURLBar.removeAttribute("readonly");
gURLBar.setAttribute("enablehistory", "true");
}
var goButtonStack = document.getElementById("go-button-stack");
if (goButtonStack)
goButtonStack.removeAttribute("hidden");
return false; // Dismiss the notification message
}
/**
* Utility class to handle manipulations of the identity indicators in the UI
*/
@ -5696,7 +5630,7 @@ IdentityHandler.prototype = {
// Cache the most recently seen SSLStatus and URI to prevent unnecessary updates
_lastStatus : null,
_lastURI : null,
_lastHost : null,
/**
* Handler for mouseclicks on the "Tell me more about this website" link text
@ -5744,27 +5678,17 @@ IdentityHandler.prototype = {
/**
* Determine the identity of the page being displayed by examining its SSL cert
* (if available) and, if necessary, update the UI to reflect this. Intended to
* be called by an nsIWebProgressListener.
*
* @param nsIWebProgress webProgress
* @param nsIRequest request
* be called by onSecurityChange
*
* @param PRUint32 state
* @param AUTF8String host
*/
checkIdentity : function(state) {
var currentURI = gBrowser.currentURI;
if (currentURI.schemeIs("http") && this._lastURI.schemeIs("http"))
return;
checkIdentity : function(state, host) {
var currentStatus = gBrowser.securityUI
.QueryInterface(Components.interfaces.nsISSLStatusProvider)
.SSLStatus;
if (currentStatus == this._lastStatus && currentURI == this._lastURI) {
// No need to update, this is a no-op check
return;
}
this._lastStatus = currentStatus;
this._lastURI = currentURI;
this._lastHost = host;
if (state & Components.interfaces.nsIWebProgressListener.STATE_IDENTITY_EV_TOPLEVEL)
this.setMode(this.IDENTITY_MODE_IDENTIFIED);
@ -5802,7 +5726,7 @@ IdentityHandler.prototype = {
// it's not the only place you have to check, there can be more than one domain,
// et cetera, ad nauseum. We know the cert is valid for location.host, so
// let's just use that, it's what the status bar does too.
var icon_label = this._lastURI.host;
var icon_label = this._lastHost;
var tooltip = this._stringBundle.getFormattedString("identity.identified.verifier",
[iData.caOrg]);
}
@ -5850,7 +5774,7 @@ IdentityHandler.prototype = {
if (newMode == this.IDENTITY_MODE_DOMAIN_VERIFIED) {
var iData = this.getIdentityData();
var body = this._lastURI.host;
var body = this._lastHost;
verifier = this._stringBundle.getFormattedString("identity.identified.verifier",
[iData.caOrg]);
supplemental = this._stringBundle.getString("identity.domainverified.supplemental");
@ -5897,6 +5821,10 @@ IdentityHandler.prototype = {
// the popup is actually needed
this._identityPopup.hidden = false;
// Tell the popup to consume dismiss clicks, to avoid bug 395314
this._identityPopup.popupBoxObject
.setConsumeRollupEvent(Ci.nsIPopupBoxObject.ROLLUP_CONSUME);
// Update the popup strings
this.setPopupMessages(this._identityBox.className);

Просмотреть файл

@ -28,6 +28,7 @@
# Joe Hewitt <hewitt@netscape.com>
# Pierre Chanial <chanial@noos.fr>
# Dean Tessman <dean_tessman@hotmail.com>
# Johnathan Nightingale <johnath@mozilla.com>
#
# Alternatively, the contents of this file may be used under the terms of
# either the GNU General Public License Version 2 or later (the "GPL"), or
@ -57,7 +58,7 @@
# All DTD information is stored in a separate file so that it can be shared by
# hiddenWindow.xul.
#include browser-doctype.inc
<window id="main-window"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
@ -138,6 +139,34 @@
<popup id="placesContext"/>
<!-- Popup for site identity information -->
<panel id="identity-popup" position="after_start" hidden="true" noautofocus="true">
<hbox id="identity-popup-container" align="top">
<image id="identity-popup-icon"/>
<vbox id="identity-popup-content-box">
<!-- Title Bar -->
<label id="identity-popup-title"/>
<!-- Content area -->
<description id="identity-popup-content"/>
<description id="identity-popup-content-supplemental"/>
<description id="identity-popup-content-verifier"/>
<hbox id="identity-popup-encryption" flex="1">
<vbox>
<image id="identity-popup-encryption-icon"/>
<spacer flex="1"/>
</vbox>
<description id="identity-popup-encryption-label" flex="1"/>
</hbox>
<spacer flex="1"/>
<!-- Footer link to page info -->
<label id="identity-popup-more-info-link"
class="text-link plain"
value="&identity.moreInfoLinkText;"
onclick="getIdentityHandler().handleMoreInfoClick(event);"/>
</vbox>
</hbox>
</panel>
<tooltip id="urlTooltip">
<label crop="center" flex="1"/>
</tooltip>
@ -146,7 +175,7 @@
<!-- bookmarks toolbar tooltip -->
<tooltip id="btTooltip" noautohide="true"
onpopupshowing="return BookmarksEventHandler.fillInBTTooltip(document.tooltipNode)">
<vbox id="btTooltipTextBox" flex="1">
<vbox id="btTooltipTextBox" flex="1">
<label id="btTitleText" />
<label id="btUrlText" />
</vbox>
@ -183,7 +212,7 @@
oncommand="gotoHistoryIndex(event); event.stopPropagation();"
onclick="checkForMiddleClick(this, event);"/>
</toolbarbutton>
<toolbarbutton id="forward-button" type="menu-button" class="toolbarbutton-1 chromeclass-toolbar-additional"
chromedir="&locale.dir;"
label="&forwardCmd.label;"
@ -197,12 +226,12 @@
oncommand="gotoHistoryIndex(event); event.stopPropagation()"
onclick="checkForMiddleClick(this, event);"/>
</toolbarbutton>
<toolbarbutton id="reload-button" class="toolbarbutton-1 chromeclass-toolbar-additional"
label="&reloadCmd.label;"
command="Browser:Reload"
tooltiptext="&reloadButton.tooltip;"/>
<toolbarbutton id="stop-button" class="toolbarbutton-1 chromeclass-toolbar-additional"
label="&stopCmd.label;"
command="Browser:Stop"
@ -221,30 +250,36 @@
<textbox id="urlbar" flex="1"
chromedir="&locale.dir;"
type="autocomplete"
autocompletesearch="history"
autocompletesearch="history"
autocompletepopup="PopupAutoComplete"
completeselectedindex="true"
tabscrolling="true"
showcommentcolumn="true"
showimagecolumn="true"
showimagecolumn="true"
enablehistory="true"
maxrows="10"
newlines="stripsurroundingwhitespace"
oninput="gBrowser.userTypedValue = this.value"
oninput="URLBarOnInput(event);"
ontextentered="return handleURLBarCommand(param);"
ontextreverted="return handleURLBarRevert();">
<deck id="page-proxy-deck" onclick="PageProxyClickHandler(event);">
<image id="page-proxy-button"
ondraggesture="PageProxyDragGesture(event);"
tooltiptext="&proxyIcon.tooltip;"/>
<image id="page-proxy-favicon" validate="never"
ondraggesture="PageProxyDragGesture(event);"
onload="this.parentNode.selectedIndex = 1;
event.stopPropagation();"
onerror="this.removeAttribute('src');
this.parentNode.selectedIndex = 0;"
tooltiptext="&proxyIcon.tooltip;"/>
</deck>
<!-- Use onclick instead of normal popup= syntax since the popup
code fires onmousedown, and hence eats our favicon drag events -->
<box id="identity-box" align="center"
onclick="getIdentityHandler().handleIdentityClick(event);">
<deck id="page-proxy-deck" onclick="PageProxyClickHandler(event);">
<image id="page-proxy-button"
ondraggesture="PageProxyDragGesture(event);"
tooltiptext="&proxyIcon.tooltip;"/>
<image id="page-proxy-favicon" validate="never"
ondraggesture="PageProxyDragGesture(event);"
onload="this.parentNode.selectedIndex = 1;
event.stopPropagation();"
onerror="this.removeAttribute('src');
this.parentNode.selectedIndex = 0;"
tooltiptext="&proxyIcon.tooltip;"/>
</deck>
<label id="identity-icon-label"/>
</box>
<hbox id="urlbar-icons">
<button type="menu"
style="-moz-user-focus: none"
@ -257,7 +292,6 @@
oncommand="return FeedHandler.subscribeToFeed(null, event);"
onclick="checkForMiddleClick(this, event);"/>
</button>
<image id="lock-icon" onclick="if (event.button == 0) displaySecurityInfo(); event.stopPropagation();"/>
#ifdef MOZ_SAFE_BROWSING
<image id="safebrowsing-urlbar-icon" tooltiptext="&safeb.urlbaricon.tooltip;"
level="safe"
@ -282,7 +316,7 @@
</hbox>
</toolbaritem>
<toolbaritem id="search-container" title="&searchItem.title;"
<toolbaritem id="search-container" title="&searchItem.title;"
align="center" class="chromeclass-toolbar-additional"
flex="100" persist="width">
<searchbar id="searchbar" flex="1" chromedir="&locale.dir;"
@ -299,7 +333,7 @@
<toolbaritem flex="1" id="personal-bookmarks" title="&bookmarksItem.title;">
<hbox id="bookmarksBarContent" flex="1" type="places"
context="placesContext" asyncinit="true"
context="placesContext" asyncinit="true"
onclick="BookmarksEventHandler.onClick(event);"
oncommand="BookmarksEventHandler.onCommand(event);"
onpopupshowing="BookmarksEventHandler.onPopupShowing(event);"
@ -333,7 +367,7 @@
tooltiptext="&newTabButton.tooltip;"
ondragover="nsDragAndDrop.dragOver(event, newTabButtonObserver);"
ondragdrop="nsDragAndDrop.drop(event, newTabButtonObserver);"
ondragexit="nsDragAndDrop.dragExit(event, newTabButtonObserver);"/>
ondragexit="nsDragAndDrop.dragExit(event, newTabButtonObserver);"/>
<toolbarbutton id="new-window-button" class="toolbarbutton-1 chromeclass-toolbar-additional"
label="&newNavigatorCmd.label;"
@ -362,7 +396,7 @@
<toolbar id="nav-bar" class="toolbar-primary chromeclass-toolbar"
toolbarname="&navbarCmd.label;" accesskey="&navbarCmd.accesskey;"
fullscreentoolbar="true" mode="icons"
fullscreentoolbar="true" mode="icons"
customizable="true"
#ifdef XP_MACOSX
defaultset="back-button,forward-button,reload-button,stop-button,home-button,urlbar-container,splitter,search-container,throbber-box"
@ -387,28 +421,28 @@
</hbox>
#endif
</toolbar>
<toolbarset id="customToolbars" context="toolbar-context-menu"/>
<toolbar id="PersonalToolbar" mode="icons" iconsize="small"
<toolbar id="PersonalToolbar" mode="icons" iconsize="small"
class="chromeclass-directories"
context="toolbar-context-menu"
context="toolbar-context-menu"
defaultset="bookmarksBarShowPlaces,personal-bookmarks"
toolbarname="&personalbarCmd.label;" accesskey="&personalbarCmd.accesskey;"
customizable="true"/>
</toolbox>
<hbox flex="1" id="browser">
<vbox id="sidebar-box" hidden="true" class="chromeclass-extrachrome">
<sidebarheader align="center">
<label id="sidebar-title" persist="value" flex="1" crop="end" control="sidebar"/>
<image id="sidebar-throbber"/>
<toolbarbutton class="tabs-closebutton" tooltiptext="&sidebarCloseButton.tooltip;" oncommand="toggleSidebar();"/>
</sidebarheader>
</sidebarheader>
<browser id="sidebar" flex="1" autoscroll="false"
style="min-width: 14em; width: 18em; max-width: 36em;"/>
</vbox>
</vbox>
<splitter id="sidebar-splitter" class="chromeclass-extrachrome" hidden="true"/>
<vbox id="appcontent" flex="1">
<tabbrowser id="content" disablehistory="true"
@ -430,7 +464,7 @@
#endif
<findbar browserid="content" id="FindToolbar"/>
<statusbar class="chromeclass-status" id="status-bar"
ondragdrop="nsDragAndDrop.drop(event, contentAreaDNDObserver);">
<statusbarpanel id="statusbar-display" label="" flex="1"/>
@ -439,8 +473,8 @@
</statusbarpanel>
<statusbarpanel id="security-button" class="statusbarpanel-iconic-text"
ondblclick="if (event.button == 0) displaySecurityInfo();"/>
<statusbarpanel id="page-report-button" type="menu"
class="statusbarpanel-menu-iconic"
<statusbarpanel id="page-report-button" type="menu"
class="statusbarpanel-menu-iconic"
tooltiptext="&pageReportIcon.tooltip;">
<menupopup onpopupshowing="gPopupBlockerObserver.fillPopupList(event);">
<menuitem observes="blockedPopupAllowSite"/>
@ -451,4 +485,4 @@
</statusbarpanel>
</statusbar>
</window>

Просмотреть файл

@ -59,7 +59,7 @@
windowtype="Browser:page-info"
onload="onLoadPageInfo()"
onunload="onUnloadPageInfo()"
xmlns:xhtml="http://www.w3.org/1999/xhtml">
xmlns:xhtml="http://www.w3.org/1999/xhtml"
align="stretch"
screenX="10" screenY="10"
width="&pageInfoWindow.width;" height="&pageInfoWindow.height;"

Просмотреть файл

@ -1699,22 +1699,26 @@
<body>
<![CDATA[
var tabStrip = this.mTabContainer.mTabstrip;
var ltr = (window.getComputedStyle(this.parentNode, null).direction
== "ltr");
// autoscroll the tab strip if we drag over the scroll
// buttons, even if we aren't dragging a tab, but then
// return to avoid drawing the drop indicator
var pixelsToScroll = 0;
var targetAnonid = aEvent.originalTarget.getAttribute("anonid");
if (targetAnonid == "scrollbutton-up") {
pixelsToScroll = tabStrip.scrollIncrement * -1;
tabStrip.scrollByPixels(pixelsToScroll);
}
else if (targetAnonid == "scrollbutton-down" ||
(targetAnonid == "alltabs-button" &&
this.mTabContainer.getAttribute("overflow") == "true")) {
pixelsToScroll = tabStrip.scrollIncrement;
tabStrip.scrollByPixels(pixelsToScroll);
if (this.mTabContainer.getAttribute("overflow") == "true") {
var targetAnonid = aEvent.originalTarget.getAttribute("anonid");
switch (targetAnonid) {
case "scrollbutton-up":
pixelsToScroll = tabStrip.scrollIncrement * -1;
break;
case "scrollbutton-down":
case "alltabs-button":
pixelsToScroll = tabStrip.scrollIncrement;
break;
}
if (pixelsToScroll)
tabStrip.scrollByPixels((ltr ? 1 : -1) * pixelsToScroll);
}
var isTabDrag = (aDragSession.sourceNode &&
@ -1742,9 +1746,10 @@
var maxMargin = Math.min(minMargin + tabStripBoxObject.width,
ib.boxObject.x + ib.boxObject.width -
ind.boxObject.width);
if (!ltr)
[minMargin, maxMargin] = [this.boxObject.width - maxMargin,
this.boxObject.width - minMargin];
var newMargin, tabBoxObject;
var ltr = (window.getComputedStyle(this.parentNode, null).direction
== "ltr");
if (pixelsToScroll) {
// if we are scrolling, put the drop indicator at the edge
// so that it doesn't jump while scrolling
@ -1775,10 +1780,7 @@
newMargin = maxMargin;
}
if (ltr)
ind.style.marginLeft = newMargin + 'px';
else
ind.style.marginRight = newMargin + 'px';
ind.style.MozMarginStart = newMargin + 'px';
ib.collapsed = !aDragSession.canDrop;
]]>

Просмотреть файл

@ -38,54 +38,9 @@
#
# ***** END LICENSE BLOCK *****
<bindings id="urlbarBindings" xmlns="http://www.mozilla.org/xbl"
xmlns:html="http://www.w3.org/1999/xhtml"
xmlns:xul="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
xmlns:xbl="http://www.mozilla.org/xbl">
<bindings id="urlbarBindings" xmlns="http://www.mozilla.org/xbl">
<binding id="urlbar" extends="chrome://global/content/bindings/autocomplete.xml#autocomplete">
<content sizetopopup="pref">
<xul:hbox class="autocomplete-textbox-container" flex="1">
<children includes="image|deck|stack">
<xul:image class="autocomplete-icon" allowevents="true"/>
</children>
<xul:stack flex="1" class="textbox-stack">
<xul:hbox anonid="textbox-input-box" class="textbox-input-box"
flex="1" xbl:inherits="tooltiptext=inputtooltiptext">
<children/>
<html:input anonid="input" class="autocomplete-textbox textbox-input"
flex="1" allowevents="true"
xbl:inherits="tooltiptext=inputtooltiptext,onfocus,onblur,value,type,maxlength,disabled,size,readonly,userAction"/>
</xul:hbox>
<xul:hbox anonid="presentation-box" class="formatted-url" flex="1"
onmousedown="focus();" hidden="true">
<xul:scrollbox anonid="presentation" class="formatted-url-contents" flex="1"
onoverflow="_contentIsCropped = true;"
onunderflow="_contentIsCropped = false;">
<xul:hbox anonid="prePath" class="formatted-url-prePath">
<xul:label anonid="protocol" class="formatted-url-protocol"/>
<xul:label anonid="subdomain" class="formatted-url-subdomain"/>
<xul:label anonid="domain" class="formatted-url-domain"/>
<xul:label anonid="port" class="formatted-url-port"/>
</xul:hbox>
<xul:label anonid="path" class="formatted-url-path"/>
</xul:scrollbox>
<xul:label anonid="overflow-ellipsis" class="formatted-url-ellipsis"
value="&#8230;" hidden="true"/>
</xul:hbox>
</xul:stack>
<children includes="hbox"/>
</xul:hbox>
<xul:dropmarker anonid="historydropmarker" class="autocomplete-history-dropmarker"
allowevents="true"
xbl:inherits="open,enablehistory"/>
<xul:popupset anonid="popupset" class="autocomplete-result-popupset"/>
</content>
<implementation implements="nsIObserver, nsIDOMEventListener">
<constructor><![CDATA[
this._ioService = Components.classes["@mozilla.org/network/io-service;1"]
@ -96,91 +51,49 @@
.QueryInterface(Components.interfaces.nsIPrefBranch2);
this._prefs.addObserver("", this, false);
this._hideProtocols = this._prefs.getCharPref("hideProtocols").split(" ");
this._animateBlend = this._prefs.getBoolPref("animateBlend");
this.clickSelectsAll = this._prefs.getBoolPref("clickSelectsAll");
this.doubleClickSelectsAll = this._prefs.getBoolPref("doubleClickSelectsAll");
this.completeDefaultIndex = this._prefs.getBoolPref("autoFill");
this._inputBox = document.getAnonymousElementByAttribute(this, "anonid", "textbox-input-box");
this._presentationBox = document.getAnonymousElementByAttribute(this, "anonid", "presentation-box");
this._overflowEllipsis = document.getAnonymousElementByAttribute(this, "anonid", "overflow-ellipsis");
this._prePath = document.getAnonymousElementByAttribute(this, "anonid", "prePath");
this._protocol = document.getAnonymousElementByAttribute(this, "anonid", "protocol");
this._subDomain = document.getAnonymousElementByAttribute(this, "anonid", "subdomain");
this._domain = document.getAnonymousElementByAttribute(this, "anonid", "domain");
this._port = document.getAnonymousElementByAttribute(this, "anonid", "port");
this._path = document.getAnonymousElementByAttribute(this, "anonid", "path");
this._urlTooltip = document.getElementById("urlTooltip");
this.inputField.controllers.insertControllerAt(0, this._copyCutController);
this.inputField.addEventListener("mousedown", this, false);
this._blendingTimers = [];
this.inputField.addEventListener("mousemove", this, false);
this.inputField.addEventListener("mouseout", this, false);
]]></constructor>
<destructor><![CDATA[
this._prefs.removeObserver("", this);
this._prefs = null;
this._ioService = null;
this._tldService = null;
this.inputField.controllers.removeController(this._copyCutController);
this.inputField.removeEventListener("mousedown", this, false);
this.inputField.removeEventListener("mousemove", this, false);
this.inputField.removeEventListener("mouseout", this, false);
]]></destructor>
<!-- initially empty fields:
<field name="_uri"/>
<field name="_protocolHidden"/>
<field name="_focused"/>
<field name="_mouseover"/>
<field name="_tooltipTimer"/>
<field name="_tldService"/>
<field name="_formatted"/>
-->
<property name="plain" onget="return !this._formatted">
<setter><![CDATA[
this._formatted = !val;
while (this._blendingTimers.length)
clearTimeout(this._blendingTimers.pop());
if (val) {
this._inputBox.style.removeProperty("opacity");
this._presentationBox.hidden = true;
} else {
this._inputBox.style.setProperty("opacity", "0", "important");
}
this._presentationBox.style.removeProperty("opacity");
this._hideURLTooltip();
return val;
]]></setter>
</property>
<property name="tldService" readonly="true">
<getter><![CDATA[
if (!this._tldService) {
this._tldService =
Components.classes["@mozilla.org/network/effective-tld-service;1"]
.getService(Components.interfaces.nsIEffectiveTLDService);
}
return this._tldService;
]]></getter>
</property>
<property name="_contentIsCropped"
onget="return !this._overflowEllipsis.hidden;"
onset="this._overflowEllipsis.hidden = !val; return val;"/>
<property name="value"
onget="return this.inputField.value;">
<setter><![CDATA[
this.mIgnoreInput = true;
this._syncValue(val);
if (val != "") {
var uri;
try {
uri = this._ioService.newURI(val, null, null);
} catch(e) {}
if (uri) {
val = uri.spec;
try {
// try to decode as UTF-8
val = decodeURI(val);
} catch(e) {}
}
}
this.inputField.value = val;
this.mIgnoreInput = false;
if (this._focused)
this.plain = true;
else if (!this._mouseover || !this.plain)
this._prettyView(false);
var event = document.createEvent("Events");
event.initEvent("ValueChange", true, true);
this.inputField.dispatchEvent(event);
@ -188,165 +101,20 @@
]]></setter>
</property>
<method name="_syncValue">
<parameter name="aValue"/>
<body><![CDATA[
var value = aValue != null ? aValue : this.value;
if (value == "") {
this._uri = null;
} else {
try {
this._uri = this._ioService.newURI(value, null, null);
// next line throws if .host is not defined
this._uri.host;
} catch(e) {
this._uri = null;
}
}
if (!this._uri) {
this._contentIsCropped = false;
if (aValue != null)
this.inputField.value = aValue;
return;
}
if (!this._focused || aValue != null) {
value = this._uri.spec;
try {
// try to decode as UTF-8
value = decodeURI(value);
} catch(e) {}
this.inputField.value = value;
}
this._protocol.setAttribute("value", this._uri.scheme + "://");
this._protocolHidden = this._hideProtocols.indexOf(this._uri.scheme) > -1;
var host = this._uri.host;
if (host) {
var subdomain;
var port = (this._uri.port > -1) ? ":" + this._uri.port : "";
if (this._uri.hostPort[0] == "[") {
// IPv6 address
subdomain = "[";
port = "]" + port;
}
else if (0 && !/^[.0-9]+$/.test(host)) {
//XXX subdomain detection disabled (bug 386727)
//XXX subdomain detection disabled for IP addresses (bug 364129)
// getEffectiveTLDLength might convert our host and return a misleading length.
// To avoid this, pass the ASCII host, count the dots of its effective TLD
// and use that number to operate on our actual host.
var asciiHost = this._uri.asciiHost;
var domainSegments = host.split(".");
var cSubdomain = domainSegments.length -
asciiHost.slice(asciiHost.length -
this.tldService.getEffectiveTLDLength(asciiHost))
.split(".").length - 1;
if (cSubdomain > 0) {
host = domainSegments;
subdomain = host.splice(0, cSubdomain).join(".") + ".";
host = host.join(".");
}
} else {
subdomain = "";
}
this._subDomain.setAttribute("value", subdomain);
this._domain.setAttribute("value", host);
this._port.setAttribute("value", port);
} else {
this._subDomain.removeAttribute("value");
this._domain.removeAttribute("value");
this._port.removeAttribute("value");
}
var path = this._uri.path;
try {
// try to decode as UTF-8
path = decodeURI(path);
} catch(e) {}
this._path.setAttribute("value", path);
]]></body>
</method>
<method name="_initPrettyView">
<body><![CDATA[
this._plain = false;
this._protocol.hidden = false;
this._presentationBox.hidden = false;
this._prePath.width = "";
if (this._protocolHidden) {
this._prePath.width = this._prePath.boxObject.width;
this._protocol.hidden = true;
}
]]></body>
</method>
<method name="_prettyView">
<parameter name="aAnimateBlend"/>
<body><![CDATA[
if (!this._uri) {
this.plain = true;
return;
}
if (!aAnimateBlend || !this._animateBlend) {
this._initPrettyView();
this.plain = false;
return;
}
const INITIAL_DELAY = 150;
const FRAME_LENGTH = 60;
const DECLINATION_REL = .2;
const DECLINATION_ABS = .15;
var inputBox = this._inputBox;
var presentationBox = this._presentationBox;
var self = this;
var opacity = parseFloat(document.defaultView.getComputedStyle(inputBox, null).opacity);
var delay = INITIAL_DELAY;
function processFrame(opacity, init) {
inputBox.style.setProperty("opacity", opacity, "important");
presentationBox.style.setProperty("opacity", 1-opacity, "important");
if (init)
self._initPrettyView();
if (!opacity)
self.plain = false;
}
while (opacity > 0) {
opacity -= opacity * DECLINATION_REL + DECLINATION_ABS;
if (opacity < 0)
opacity = 0;
this._blendingTimers.push(setTimeout(processFrame, delay, opacity, delay == INITIAL_DELAY));
delay += FRAME_LENGTH;
}
]]></body>
</method>
<method name="_initURLTooltip">
<parameter name="aCallback"/>
<parameter name="aObject"/>
<parameter name="aCrop"/>
<body><![CDATA[
if (this.focused)
return;
if (this._tooltipTimer)
clearTimeout(this._tooltipTimer);
this._tooltipTimer = setTimeout(function(self) {
this._tooltipTimer = setTimeout(function (self) {
self._tooltipTimer = 0;
var tooltipText = aCallback.apply(aObject);
if (tooltipText) {
var label = self._urlTooltip.firstChild;
label.value = tooltipText;
label.crop = aCrop || "center";
var bO = self.boxObject;
self._urlTooltip.maxWidth = bO.width;
self._urlTooltip.showPopup(self, bO.screenX, bO.screenY + bO.height, "tooltip");
}
}, 400, this);
var label = self._urlTooltip.firstChild;
label.value = self.value;
var bO = self.boxObject;
self._urlTooltip.maxWidth = bO.width;
self._urlTooltip.showPopup(self, bO.screenX, bO.screenY + bO.height, "tooltip");
}, 700, this);
]]></body>
</method>
@ -411,12 +179,6 @@
<body><![CDATA[
if (aTopic == "nsPref:changed") {
switch(aData) {
case "hideProtocols":
this._hideProtocols = this._prefs.getCharPref(aData).split(" ");
this._syncValue();
if (!this.plain)
this._prettyView(false);
break;
case "clickSelectsAll":
case "doubleClickSelectsAll":
this[aData] = this._prefs.getBoolPref(aData);
@ -424,9 +186,6 @@
case "autoFill":
this.completeDefaultIndex = this._prefs.getBoolPref(aData);
break;
case "animateBlend":
this._animateBlend = this._prefs.getBoolPref(aData);
break;
}
}
]]></body>
@ -435,71 +194,27 @@
<method name="handleEvent">
<parameter name="aEvent"/>
<body><![CDATA[
if (aEvent.type == "mousedown" &&
aEvent.button == 0 && aEvent.detail == 2 &&
this.doubleClickSelectsAll) {
this.editor.selectAll();
aEvent.preventDefault();
switch (aEvent.type) {
case "mousedown":
if (this.doubleClickSelectsAll &&
aEvent.button == 0 && aEvent.detail == 2) {
this.editor.selectAll();
aEvent.preventDefault();
}
break;
case "mousemove":
this._initURLTooltip();
break;
case "mouseout":
this._hideURLTooltip();
break;
}
]]></body>
</method>
</implementation>
<handlers>
<handler event="input"
action="this._syncValue();"/>
<handler event="mousemove"><![CDATA[
if (!this._focused && this._contentIsCropped)
this._initURLTooltip(function() {
return this.plain ? this.value : null;
}, this, "start");
]]></handler>
<handler event="mouseover"><![CDATA[
if (this._mouseover)
return;
if (!this.plain) {
// do nothing if we're over the favicon, history dropmarker et al
var pBO = this._presentationBox.boxObject;
if (event.screenX < pBO.screenX || event.screenX > pBO.screenX + pBO.width)
return;
}
this._mouseover = true;
setTimeout(function(self) {
if (self._mouseover) {
self.plain = true;
if (!self._focused && self._contentIsCropped)
self._initURLTooltip(function() {
return this.plain ? this.value : null;
}, self, "start");
}
}, 60, this);
]]></handler>
<handler event="mouseout" phase="target"><![CDATA[
this._mouseover = false;
if (!this._focused && this.plain)
this._prettyView(true);
else
this._hideURLTooltip();
]]></handler>
<handler event="focus" phase="capturing"><![CDATA[
if (!this._focused) {
this._focused = true;
this.plain = true;
}
]]></handler>
<handler event="blur" phase="capturing"><![CDATA[
if (this._focused && !this._dontBlur) {
this._focused = false;
this._syncValue();
if (!this._mouseover)
this._prettyView(true);
}
]]></handler>
<handler event="focus" phase="capturing" action="this._hideURLTooltip();"/>
</handlers>
</binding>

Просмотреть файл

@ -1532,7 +1532,7 @@ nsIEProfileMigrator::CopyCookies(PRBool aReplace)
{
// IE cookies are stored in files named <username>@domain[n].txt
// (in <username>'s Cookies folder. isn't the naming redundant?)
PRBool rv = NS_OK;
nsresult rv = NS_OK;
nsCOMPtr<nsIFile> cookiesDir;
nsCOMPtr<nsISimpleEnumerator> cookieFiles;
@ -1543,8 +1543,33 @@ nsIEProfileMigrator::CopyCookies(PRBool aReplace)
// find the cookies directory
NS_GetSpecialDirectory(NS_WIN_COOKIES_DIR, getter_AddRefs(cookiesDir));
if (cookiesDir)
cookiesDir->GetDirectoryEntries(getter_AddRefs(cookieFiles));
if (!cookiesDir)
return NS_ERROR_FAILURE;
// Check for Vista's UAC, if so, tack on a "Low" sub dir
nsCOMPtr<nsIWindowsRegKey> regKey =
do_CreateInstance("@mozilla.org/windows-registry-key;1");
if (regKey) {
NS_NAMED_LITERAL_STRING(regPath,"Software\\Microsoft\\Windows\\CurrentVersion\\Policies\\System");
if (NS_SUCCEEDED(regKey->Open(nsIWindowsRegKey::ROOT_KEY_LOCAL_MACHINE,
regPath,
nsIWindowsRegKey::ACCESS_QUERY_VALUE))) {
PRUint32 value;
if (NS_SUCCEEDED(regKey->ReadIntValue(NS_LITERAL_STRING("EnableLUA"),
&value)) &&
value == 1) {
nsAutoString dir;
// For cases where we are running under protected mode, check
// cookiesDir for the Low sub directory. (Simpler than using
// process token calls to check our Vista integrity level.)
cookiesDir->GetLeafName(dir);
if (!dir.EqualsLiteral("Low"))
cookiesDir->Append(NS_LITERAL_STRING("Low"));
}
}
}
cookiesDir->GetDirectoryEntries(getter_AddRefs(cookieFiles));
if (!cookieFiles)
return NS_ERROR_FAILURE;

Просмотреть файл

@ -44,6 +44,6 @@ function searchBookmarks(aSearchString) {
if (!aSearchString)
tree.place = tree.place;
else
tree.applyFilter(aSearchString, true);
tree.applyFilter(aSearchString, true,
[PlacesUtils.bookmarksRootId, PlacesUtils.unfiledRootId]);
}

Просмотреть файл

@ -67,7 +67,7 @@
oncommand="searchBookmarks(this.value);"/>
</hbox>
<tree id="bookmarks-view" class="placesTree" type="places"
<tree id="bookmarks-view" class="sidebar-placesTree" type="places"
flex="1"
hidecolumnpicker="true"
place="place:folder=2&amp;queryType=1"
@ -77,6 +77,6 @@
<treecols>
<treecol id="title" flex="1" primary="true" hideheader="true"/>
</treecols>
<treechildren id="bookmarks-view-children" view="bookmarks-view" flex="1"/>
<treechildren id="bookmarks-view-children" view="bookmarks-view" class="sidebar-placesTreechildren" flex="1"/>
</tree>
</page>

Просмотреть файл

@ -1030,39 +1030,48 @@ PlacesController.prototype = {
* elsewhere.
*/
getTransferData: function PC_getTransferData(dragAction) {
var nodes = null;
if (dragAction == Ci.nsIDragService.DRAGDROP_ACTION_COPY)
nodes = this._view.getCopyableSelection();
else
nodes = this._view.getDragableSelection();
var dataSet = new TransferDataSet();
for (var i = 0; i < nodes.length; ++i) {
var node = nodes[i];
var result = this._view.getResult();
var oldViewer = result.viewer;
try {
result.viewer = null;
var nodes = null;
if (dragAction == Ci.nsIDragService.DRAGDROP_ACTION_COPY)
nodes = this._view.getCopyableSelection();
else
nodes = this._view.getDragableSelection();
var dataSet = new TransferDataSet();
for (var i = 0; i < nodes.length; ++i) {
var node = nodes[i];
var data = new TransferData();
function addData(type, overrideURI) {
data.addDataForFlavour(type, PlacesUtils._wrapString(
PlacesUtils.wrapNode(node, type, overrideURI)));
var data = new TransferData();
function addData(type, overrideURI) {
data.addDataForFlavour(type, PlacesUtils._wrapString(
PlacesUtils.wrapNode(node, type, overrideURI)));
}
function addURIData(overrideURI) {
addData(PlacesUtils.TYPE_X_MOZ_URL, overrideURI);
addData(PlacesUtils.TYPE_UNICODE, overrideURI);
addData(PlacesUtils.TYPE_HTML, overrideURI);
}
// This order is _important_! It controls how this and other
// applications select data to be inserted based on type.
addData(PlacesUtils.TYPE_X_MOZ_PLACE);
var uri;
// Allow dropping the feed uri of live-bookmark folders
if (PlacesUtils.nodeIsLivemarkContainer(node))
uri = PlacesUtils.livemarks.getFeedURI(node.itemId).spec;
addURIData(uri);
dataSet.push(data);
}
function addURIData(overrideURI) {
addData(PlacesUtils.TYPE_X_MOZ_URL, overrideURI);
addData(PlacesUtils.TYPE_UNICODE, overrideURI);
addData(PlacesUtils.TYPE_HTML, overrideURI);
}
// This order is _important_! It controls how this and other
// applications select data to be inserted based on type.
addData(PlacesUtils.TYPE_X_MOZ_PLACE);
var uri;
// Allow dropping the feed uri of live-bookmark folders
if (PlacesUtils.nodeIsLivemarkContainer(node))
uri = PlacesUtils.livemarks.getFeedURI(node.itemId).spec;
addURIData(uri);
dataSet.push(data);
}
finally {
if (oldViewer)
result.viewer = oldViewer;
}
return dataSet;
},
@ -1071,63 +1080,69 @@ PlacesController.prototype = {
* Copy Bookmarks and Folders to the clipboard
*/
copy: function PC_copy() {
var nodes = this._view.getCopyableSelection();
var result = this._view.getResult();
var oldViewer = result.viewer;
try {
result.viewer = null;
var nodes = this._view.getCopyableSelection();
var xferable =
Cc["@mozilla.org/widget/transferable;1"].
createInstance(Ci.nsITransferable);
var foundFolder = false, foundLink = false;
var copiedFolders = [];
var placeString = mozURLString = htmlString = unicodeString = "";
var xferable = Cc["@mozilla.org/widget/transferable;1"].
createInstance(Ci.nsITransferable);
var foundFolder = false, foundLink = false;
var copiedFolders = [];
var placeString = mozURLString = htmlString = unicodeString = "";
for (var i = 0; i < nodes.length; ++i) {
var node = nodes[i];
if (this._shouldSkipNode(node, copiedFolders))
continue;
if (PlacesUtils.nodeIsFolder(node))
copiedFolders.push(node);
for (var i = 0; i < nodes.length; ++i) {
var node = nodes[i];
if (this._shouldSkipNode(node, copiedFolders))
continue;
if (PlacesUtils.nodeIsFolder(node))
copiedFolders.push(node);
function generateChunk(type, overrideURI) {
var suffix = i < (nodes.length - 1) ? NEWLINE : "";
var uri = overrideURI;
function generateChunk(type, overrideURI) {
var suffix = i < (nodes.length - 1) ? NEWLINE : "";
var uri = overrideURI;
if (PlacesUtils.nodeIsLivemarkContainer(node))
uri = PlacesUtils.livemarks.getFeedURI(node.itemId).spec
mozURLString += (PlacesUtils.wrapNode(node, PlacesUtils.TYPE_X_MOZ_URL,
uri) + suffix);
unicodeString += (PlacesUtils.wrapNode(node, PlacesUtils.TYPE_UNICODE,
uri) + suffix);
htmlString += (PlacesUtils.wrapNode(node, PlacesUtils.TYPE_HTML,
uri) + suffix);
if (PlacesUtils.nodeIsLivemarkContainer(node))
uri = PlacesUtils.livemarks.getFeedURI(node.itemId).spec
mozURLString += (PlacesUtils.wrapNode(node, PlacesUtils.TYPE_X_MOZ_URL,
uri) + suffix);
unicodeString += (PlacesUtils.wrapNode(node, PlacesUtils.TYPE_UNICODE,
uri) + suffix);
htmlString += (PlacesUtils.wrapNode(node, PlacesUtils.TYPE_HTML,
uri) + suffix);
var placeSuffix = i < (nodes.length - 1) ? "," : "";
return PlacesUtils.wrapNode(node, type, overrideURI) + placeSuffix;
var placeSuffix = i < (nodes.length - 1) ? "," : "";
return PlacesUtils.wrapNode(node, type, overrideURI) + placeSuffix;
}
// all items wrapped as TYPE_X_MOZ_PLACE
placeString += generateChunk(PlacesUtils.TYPE_X_MOZ_PLACE);
}
// all items wrapped as TYPE_X_MOZ_PLACE
placeString += generateChunk(PlacesUtils.TYPE_X_MOZ_PLACE);
}
function addData(type, data) {
xferable.addDataFlavor(type);
xferable.setTransferData(type, PlacesUtils._wrapString(data), data.length * 2);
}
// This order is _important_! It controls how this and other applications
// select data to be inserted based on type.
if (placeString)
addData(PlacesUtils.TYPE_X_MOZ_PLACE, placeString);
if (mozURLString)
addData(PlacesUtils.TYPE_X_MOZ_URL, mozURLString);
if (unicodeString)
addData(PlacesUtils.TYPE_UNICODE, unicodeString);
if (htmlString)
addData(PlacesUtils.TYPE_HTML, htmlString);
function addData(type, data) {
xferable.addDataFlavor(type);
xferable.setTransferData(type, PlacesUtils._wrapString(data), data.length * 2);
if (placeString || unicodeString || htmlString || mozURLString) {
PlacesUtils.clipboard.setData(xferable, null, Ci.nsIClipboard.kGlobalClipboard);
}
}
// This order is _important_! It controls how this and other applications
// select data to be inserted based on type.
if (placeString)
addData(PlacesUtils.TYPE_X_MOZ_PLACE, placeString);
if (mozURLString)
addData(PlacesUtils.TYPE_X_MOZ_URL, mozURLString);
if (unicodeString)
addData(PlacesUtils.TYPE_UNICODE, unicodeString);
if (htmlString)
addData(PlacesUtils.TYPE_HTML, htmlString);
if (placeString || unicodeString || htmlString || mozURLString) {
var clipboard =
Cc["@mozilla.org/widget/clipboard;1"].getService(Ci.nsIClipboard);
clipboard.setData(xferable, null, Ci.nsIClipboard.kGlobalClipboard);
finally {
if (oldViewer)
result.viewer = oldViewer;
}
},
@ -1166,8 +1181,7 @@ PlacesController.prototype = {
return xferable;
}
var clipboard = Cc["@mozilla.org/widget/clipboard;1"].
getService(Ci.nsIClipboard);
var clipboard = PlacesUtils.clipboard;
var ip = this._view.insertionPoint;
if (!ip)
@ -1221,6 +1235,285 @@ PlacesController.prototype = {
}
};
function PlacesMenuDNDObserver(aView, aPopup) {
this._view = aView;
this._popup = aPopup;
this._popup.addEventListener("draggesture", this, false);
this._popup.addEventListener("dragover", this, false);
this._popup.addEventListener("dragdrop", this, false);
this._popup.addEventListener("dragexit", this, false);
}
/**
* XXXmano-please-rewrite-me: This code was ported over from menu.xul in bug 399729.
* Unsurprisngly it's still mostly broken due to bug 337761, thus I didn't bother
* trying to cleaning up this extremely buggy over-folder detection code yet.
*/
PlacesMenuDNDObserver.prototype = {
_view: null,
_popup: null,
// Sub-menus should be opened when the mouse drags over them, and closed
// when the mouse drags off. The overFolder object manages opening and closing
// of folders when the mouse hovers.
_overFolder: {node: null, openTimer: null, hoverTime: 350, closeTimer: null},
// If this menu's parent auto-opened it because it was dragged over, but didn't
// close it because the mouse dragged into it, the menu should close itself
// onDragExit. This timer is set in dragExit to close the menu.
_closeMenuTimer: null,
_setTimer: function TBV_DO_setTimer(time) {
var timer = Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer);
timer.initWithCallback(this, time, timer.TYPE_ONE_SHOT);
return timer;
},
// Function to process all timer notifications.
notify: function TBV_DO_notify(timer) {
// Timer to open a submenu that's being dragged over.
if (timer == this._overFolder.openTimer) {
this._overFolder.node.lastChild.setAttribute("autoopened", "true");
this._overFolder.node.lastChild.showPopup(this._overFolder.node);
this._overFolder.openTimer = null;
}
// Timer to close a submenu that's been dragged off of.
if (timer == this._overFolder.closeTimer) {
// Only close the submenu if the mouse isn't being dragged over any
// of its child menus.
var draggingOverChild =
PlacesControllerDragHelper.draggingOverChildNode(this._overFolder.node);
if (draggingOverChild)
this._overFolder.node = null;
this._clearOverFolder();
// Close any parent folders which aren't being dragged over.
// (This is necessary because of the above code that keeps a folder
// open while its children are being dragged over.)
if (!draggingOverChild)
this._closeParentMenus();
}
// Timer to close this menu after the drag exit.
if (timer == this._closeMenuTimer) {
if (!PlacesControllerDragHelper.draggingOverChildNode(this._popup)) {
this._popup.hidePopup();
// Close any parent menus that aren't being dragged over;
// otherwise they'll stay open because they couldn't close
// while this menu was being dragged over.
this._closeParentMenus();
}
}
},
// Helper function to close all parent menus of this menu,
// as long as none of the parent's children are currently being
// dragged over.
_closeParentMenus: function TBV_DO_closeParentMenus() {
var parent = this._popup.parentNode;
while (parent) {
if (parent.nodeName == "menupopup" && parent._resultNode) {
if (PlacesControllerDragHelper.draggingOverChildNode(parent.parentNode))
break;
parent.hidePopup();
}
parent = parent.parentNode;
}
},
// The mouse is no longer dragging over the stored menubutton.
// Close the menubutton, clear out drag styles, and clear all
// timers for opening/closing it.
_clearOverFolder: function TBV_DO_clearOverFolder() {
if (this._overFolder.node && this._overFolder.node.lastChild) {
if (!this._overFolder.node.lastChild.hasAttribute("dragover"))
this._overFolder.node.lastChild.hidePopup();
this._overFolder.node = null;
}
if (this._overFolder.openTimer) {
this._overFolder.openTimer.cancel();
this._overFolder.openTimer = null;
}
if (this._overFolder.closeTimer) {
this._overFolder.closeTimer.cancel();
this._overFolder.closeTimer = null;
}
},
// This function returns information about where to drop when
// dragging over this menu--insertion point, child index to drop
// before, and folder to drop into.
_getDropPoint: function TBV_DO_getDropPoint(event) {
// Can't drop if the menu isn't a folder
var resultNode = this._popup._resultNode;
if (!PlacesUtils.nodeIsFolder(resultNode))
return null;
var dropPoint = { ip: null, beforeIndex: null, folderNode: null };
// Loop through all the nodes to see which one this should
// get dropped in/above/below.
var start = 0;
var end = this._popup.childNodes.length;
if (this._popup == this._view && this._view.localName == "menupopup") {
// Ignore static content at the top and bottom of the menu.
start = this._view._startMarker + 1;
if (this._view._endMarker != -1)
end = this._view._endMarker;
}
for (var i = start; i < end; i++) {
var xulNode = this._popup.childNodes[i];
var nodeY = xulNode.boxObject.y - this._popup.boxObject.y;
var nodeHeight = xulNode.boxObject.height;
if (xulNode.node &&
PlacesUtils.nodeIsFolder(xulNode.node) &&
!PlacesUtils.nodeIsReadOnly(xulNode.node)) {
// This is a folder. If the mouse is in the top 25% of the
// node, drop above the folder. If it's in the middle
// 50%, drop into the folder. If it's past that, drop below.
if (event.clientY < nodeY + (nodeHeight * 0.25)) {
// Drop above this folder.
dropPoint.ip = new InsertionPoint(resultNode.itemId, i - start,
-1);
dropPoint.beforeIndex = i;
return dropPoint;
}
else if (event.clientY < nodeY + (nodeHeight * 0.75)) {
// Drop inside this folder.
dropPoint.ip = new InsertionPoint(xulNode.node.itemId, -1, 1);
dropPoint.beforeIndex = i;
dropPoint.folderNode = xulNode;
return dropPoint;
}
} else {
// This is a non-folder node. If the mouse is above the middle,
// drop above the folder. Otherwise, drop below.
if (event.clientY < nodeY + (nodeHeight / 2)) {
// Drop above this bookmark.
dropPoint.ip = new InsertionPoint(resultNode.itemId, i - start, -1);
dropPoint.beforeIndex = i;
return dropPoint;
}
}
}
// Should drop below the last node.
dropPoint.ip = new InsertionPoint(resultNode.itemId, -1, 1);
dropPoint.beforeIndex = -1;
return dropPoint;
},
// This function clears all of the dragover styles that were set when
// a menuitem was dragged over.
_clearStyles: function TBV_DO_clearStyles() {
this._popup.removeAttribute("dragover");
for (var i = 0; i < this._popup.childNodes.length; i++) {
this._popup.childNodes[i].removeAttribute("dragover-top");
this._popup.childNodes[i].removeAttribute("dragover-bottom");
this._popup.childNodes[i].removeAttribute("dragover-into");
}
},
onDragStart: function TBV_DO_onDragStart(event, xferData, dragAction) {
this._view._selection = event.target.node;
this._view._cachedInsertionPoint = undefined;
if (event.ctrlKey)
dragAction.action = Ci.nsIDragService.DRAGDROP_ACTION_COPY;
xferData.data = this._view.controller.getTransferData(dragAction.action);
},
canDrop: function TBV_DO_canDrop(event, session) {
return PlacesControllerDragHelper.canDrop(this._view, -1);
},
onDragOver: function TBV_DO_onDragOver(event, flavor, session) {
PlacesControllerDragHelper.currentDropTarget = event.target;
var dropPoint = this._getDropPoint(event);
if (dropPoint == null)
return;
this._clearStyles();
if (dropPoint.folderNode) {
// Dragging over a folder; set the appropriate styles.
if (this._overFolder.node != dropPoint.folderNode) {
this._clearOverFolder();
this._overFolder.node = dropPoint.folderNode;
this._overFolder.openTimer = this._setTimer(this._overFolder.hoverTime);
}
dropPoint.folderNode.setAttribute("dragover-into", "true");
}
else {
// Dragging over a menuitem, set dragover-top/bottom to show where
// the item will be dropped and clear out any old folder info.
if (dropPoint.beforeIndex == -1) {
if (this._popup == this._view && this._view.localName == "menupopup" &&
this._popup._endMarker != -1) {
this._popup.childNodes[this._popup._endMarker]
.setAttribute("dragover-top", "true");
}
else
this._popup.lastChild.setAttribute("dragover-bottom", "true");
}
else {
this._popup.childNodes[dropPoint.beforeIndex]
.setAttribute("dragover-top", "true");
}
// Clear out old folder information
this._clearOverFolder();
}
this._popup.setAttribute("dragover", "true");
},
onDrop: function TBV_DO_onDrop(event, dropData, session) {
var dropPoint = this._getDropPoint(event);
if (!dropPoint)
return;
PlacesControllerDragHelper.onDrop(null, this._view, dropPoint.ip);
},
onDragExit: function TBV_DO_onDragExit(event, session) {
PlacesControllerDragHelper.currentDropTarget = null;
this._clearStyles();
// Close any folder being hovered over
if (this._overFolder.node)
this._overFolder.closeTimer = this._setTimer(this._overFolder.hoverTime);
// The autoopened attribute is set when this folder was automatically
// opened after the user dragged over it. If this attribute is set,
// auto-close the folder on drag exit.
if (this._popup.hasAttribute("autoopened"))
this._closeMenuTimer = this._setTimer(this._overFolder.hoverTime);
},
getSupportedFlavours: function TBV_DO_getSupportedFlavours() {
var flavorSet = new FlavourSet();
for (var i = 0; i < this._view.peerDropTypes.length; ++i)
flavorSet.appendFlavour(this._view.peerDropTypes[i]);
return flavorSet;
},
handleEvent: function(aEvent) {
switch (aEvent.type) {
case "draggesture":
if (aEvent.target.localName != "menu" && aEvent.target.node) {
// TODO--allow menu drag if shift (or alt??) key is down
nsDragAndDrop.startDrag(aEvent, this);
}
break;
case "dragover":
nsDragAndDrop.dragOver(aEvent, this);
break;
case "dragdrop":
nsDragAndDrop.drop(aEvent, this);
break;
case "dragexit":
nsDragAndDrop.dragExit(aEvent, this);
break;
}
}
}
/**
* Handles drag and drop operations for views. Note that this is view agnostic!
* You should not use PlacesController._view within these methods, since
@ -1273,9 +1566,9 @@ var PlacesControllerDragHelper = {
* it is being dragged over, false otherwise.
*/
canDrop: function PCDH_canDrop(view, orientation) {
var parent = view.getResult().root;
if (PlacesUtils.nodeIsReadOnly(parent) ||
!PlacesUtils.nodeIsFolder(parent))
var root = view.getResult().root;
if (PlacesUtils.nodeIsReadOnly(root) ||
!PlacesUtils.nodeIsFolder(root))
return false;
var session = this.getSession();
@ -1335,21 +1628,21 @@ var PlacesControllerDragHelper = {
var xferable = this._initTransferable(session, targetView,
insertionPoint.orientation);
var dropCount = session.numDropItems;
var movedCount = 0;
for (var i = 0; i < dropCount; ++i) {
session.getData(xferable, i);
var data = { }, flavor = { };
xferable.getAnyTransferData(flavor, data, { });
data.value.QueryInterface(Ci.nsISupportsString);
// There's only ever one in the D&D case.
var unwrapped = PlacesUtils.unwrapNodes(data.value.data,
flavor.value)[0];
var index = insertionPoint.index;
// Adjust insertion index to prevent reversal of dragged items. When you
// drag multiple elts upward: need to increment index or each successive
// elt will be inserted at the same index, each above the previous.
@ -1358,7 +1651,7 @@ var PlacesControllerDragHelper = {
index = index + movedCount;
movedCount++;
}
transactions.push(PlacesUtils.makeTransaction(unwrapped,
flavor.value, insertionPoint.itemId,
index, copy));

Просмотреть файл

@ -571,11 +571,28 @@ var gEditItemOverlay = {
expander.className = "expander-up"
expander.setAttribute("tooltiptext",
expander.getAttribute("tooltiptextup"));
if (!this._folderTree.treeBoxObject.view.isContainerOpen(0))
this._folderTree.treeBoxObject.view.toggleOpenState(0);
this._folderTree.selectFolders([this._getFolderIdFromMenuList()]);
this._folderTree.collapsed = false;
this._folderTree.focus();
if (!this._folderTree.place) {
const FOLDER_TREE_PLACE_URI =
"place:folder=2&excludeItems=1&excludeQueries=1&excludeReadOnlyFolders=1";
this._folderTree.place = FOLDER_TREE_PLACE_URI;
}
var currentFolder = this._getFolderIdFromMenuList();
// Don't select anything in the tree if the item is "unfiled"
if (currentFolder == PlacesUtils.unfiledRootId)
this._folderTree.selectFolders([]);
else {
this._folderTree.selectFolders([currentFolder]);
this._folderTree.focus();
}
if ((currentFolder == PlacesUtils.bookmarksRootId ||
currentFolder == PlacesUtils.unfiledRootId) &&
!this._folderTree.treeBoxObject.view.isContainerOpen(0)) {
// Expand the root node if selectFolder didn't
this._folderTree.treeBoxObject.view.toggleOpenState(0);
}
}
},

Просмотреть файл

@ -144,7 +144,6 @@
collapsed="true"
onselect="gEditItemOverlay.onFolderTreeSelect();"
showRoot="true"
place="place:folder=2&amp;excludeItems=1&amp;excludeQueries=1&amp;excludeReadOnlyFolders=1"
hidecolumnpicker="true"
observes="paneElementsBroadcaster">
<treecols>

Просмотреть файл

@ -114,6 +114,7 @@
</hbox>
<tree id="historyTree"
class="sidebar-placesTree"
flex="1"
type="places"
context="placesContext"
@ -123,6 +124,6 @@
<treecols>
<treecol id="title" flex="1" primary="true" hideheader="true"/>
</treecols>
<treechildren flex="1"/>
<treechildren class="sidebar-placesTreechildren" flex="1"/>
</tree>
</page>

Просмотреть файл

@ -80,34 +80,21 @@
<field name="_built">false</field>
<field name="_ignoreInvalidateContainer">false</field>
<method name="onPopupShowing">
<parameter name="aEvent"/>
<body><![CDATA[
this._ensureInitialized();
if (!this._resultNode.containerOpen)
this._resultNode.containerOpen = true;
if (!this._built)
this._rebuild();
if (this.popupShowingCallback)
this.popupShowingCallback();
var popup = aEvent.target;
var resultNode = popup._resultNode;
resultNode.containerOpen = true;
if (!popup._built)
this._rebuild(popup);
if (!popup._DNDObserver)
popup._DNDObserver = new PlacesMenuDNDObserver(this, popup);
]]></body>
</method>
<field name="_selection">null</field>
<method name="setResultAndNode">
<parameter name="result"/>
<parameter name="resultNode"/>
<body><![CDATA[
this._result = result;
this._resultNode = resultNode;
this._rebuild();
]]></body>
</method>
<!-- nsIPlacesView -->
<method name="getResult">
<body><![CDATA[
@ -118,42 +105,32 @@
<!-- nsIPlacesView -->
<method name="getResultNode">
<body><![CDATA[
this._ensureInitialized();
return this._resultNode;
]]></body>
</method>
<!-- These are the indices of the start and end
of dynamic content in the menu. For index,
if this is a bookmark menu and it has two
static entries at the top, "Bookmark this page"
and "Bookmark all tabs", _startMarker will be
2. If it has an "open in tabs" item at the end,
_endMarker will be the index of that item.
If there is no static content in the menu,
_startMarker and _endMarker are -1. -->
<field name="_startMarker">-1</field>
<field name="_endMarker">-1</field>
<method name="_cleanMenu">
<parameter name="aPopup"/>
<body><![CDATA[
// Find static menuitems that should go at the start
// and end of the menu, marked by builder="start" and
// builder="end" attributes, and keep track of their indices.
// All of the items between the start and end should be removed.
var items = [];
this._startMarker = -1;
this._endMarker = -1;
for (var i = 0; i < this.childNodes.length; ++i) {
var item = this.childNodes[i];
aPopup._startMarker = -1;
aPopup._endMarker = -1;
for (var i = 0; i < aPopup.childNodes.length; ++i) {
var item = aPopup.childNodes[i];
if (item.getAttribute("builder") == "start") {
this._startMarker = i;
aPopup._startMarker = i;
continue;
}
if (item.getAttribute("builder") == "end") {
this._endMarker = i;
aPopup._endMarker = i;
continue;
}
if ((this._startMarker != -1) && (this._endMarker == -1))
if ((aPopup._startMarker != -1) && (aPopup._endMarker == -1))
items.push(item);
}
@ -161,8 +138,8 @@
// them and the static content at the end.
for (var i = 0; i < items.length; ++i) {
// skip the empty menu item
if (this._emptyMenuItem != items[i]) {
items[i].parentNode.removeChild(items[i]);
if (aPopup._emptyMenuItem != items[i]) {
aPopup.removeChild(items[i]);
if (this._endMarker > 0)
--this._endMarker;
}
@ -170,18 +147,18 @@
// If no static items were found at the beginning, remove all items before
// the static items at the end.
if (this._startMarker == -1) {
var end = (this._endMarker == -1) ? this.childNodes.length - 1 : this._endMarker - 1;
if (aPopup._startMarker == -1) {
var end = aPopup._endMarker == -1 ?
aPopup.childNodes.length - 1 : aPopup._endMarker - 1;
for (var i = end; i >=0; i--) {
// skip the empty menu item
if (this._emptyMenuItem != this.childNodes[i]) {
this.removeChild(this.childNodes[i]);
if (this._endMarker > 0)
--this._endMarker;
if (aPopup._emptyMenuItem != aPopup.childNodes[i]) {
aPopup.removeChild(aPopup.childNodes[i]);
if (aPopup._endMarker > 0)
--aPopup._endMarker;
}
}
}
//LOG("KIDS = " + this.childNodes.length);
]]></body>
</method>
@ -190,157 +167,78 @@
<body><![CDATA[
if (PlacesUtils.nodeIsContainer(child.node)) {
for (var i=0; i < this._containerNodesMap.length; i++) {
if (this._containerNodesMap[i].resultNode == child.node)
if (this._containerNodesMap[i].resultNode == child.node) {
this._containerNodesMap.splice(i, 1);
break;
}
}
}
this.removeChild(child);
child.parentNode.removeChild(child);
]]></body>
</method>
<method name="insertNewItem">
<parameter name="child"/>
<parameter name="before"/>
<parameter name="aChild"/>
<parameter name="aParentPopup"/>
<parameter name="aBefore"/>
<body><![CDATA[
const XULNS = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
var element = null;
if (PlacesUtils.nodeIsURI(child)) {
element = document.createElementNS(XULNS, "menuitem");
element.setAttribute("label", child.title);
element.setAttribute("url", child.uri);
element.setAttribute("statustext", child.uri);
element.className = "menuitem-iconic bookmark-item";
}
else if (PlacesUtils.nodeIsSeparator(child)) {
element = document.createElementNS(XULNS, "menuseparator");
}
else if (PlacesUtils.nodeIsContainer(child)) {
element = document.createElementNS(XULNS, "menu");
element.setAttribute("type", "menu");
element.setAttribute("container", "true");
element.setAttribute("label", child.title);
var element =
PlacesUtils.createMenuItemForNode(aChild, this._containerNodesMap);
if (PlacesUtils.nodeIsLivemarkContainer(child)) {
element.setAttribute("livemark", "true");
var folder = child.itemId;
var siteURI = PlacesUtils.livemarks.getSiteURI(folder);
if (siteURI)
element.setAttribute("siteURI", siteURI.spec);
}
var popup = document.createElementNS(XULNS, "menupopup");
popup.setAttribute("type", "places");
element.appendChild(popup);
#ifndef XP_MACOSX
// No context menus on menus on Mac
// The context menu is set here instead of in the xbl constructor
// because it doesn't get initialized properly if set in the constructor.
popup.setAttribute("context", "placesContext");
#endif
popup._result = this._result;
popup._resultNode = asContainer(child);
element.className = "menu-iconic bookmark-item";
#ifdef XP_MACOSX
// If this is a child of the bookmarks menubar, we have to manually attach
// its xbl binding, because it's not a dom node and the style rules don't
// get applied correctly.
if (this._needsBindingAttachment) {
const MENU_URI = "chrome://browser/content/places/menu.xml#places-menupopup";
document.addBinding(popup, MENU_URI);
}
#endif
popup._containerNodesMap = this._containerNodesMap;
this._containerNodesMap.push({ resultNode: child, domNode: popup });
}
if (element) {
element.node = child;
element.node.viewIndex = 0;
if (child.icon)
element.setAttribute("image", child.icon.spec);
if (before)
this.insertBefore(element, before);
else {
// Add the new element to the menu. If there is static content at
// the end of the menu, add the element before that. Otherwise,
// just add to the end.
if (this._endMarker != -1)
this.insertBefore(element, this.childNodes[this._endMarker++]);
else
this.appendChild(element);
}
if (aBefore)
aParentPopup.insertBefore(element, aBefore);
else {
// Add the new element to the menu. If there is static content at
// the end of the menu, add the element before that. Otherwise,
// just add to the end.
if (aParentPopup._endMarker != -1)
aParentPopup.insertBefore(element,
aParentPopup.childNodes[this._endMarker++]);
else
aParentPopup.appendChild(element);
}
]]></body>
</method>
#ifdef XP_MACOSX
<field name="_needsBindingAttachment">false</field>
#endif
<field name="_emptyMenuItem">null</field>
<method name="_showEmptyMenuItem">
<parameter name="aPopup"/>
<body><![CDATA[
if (this._emptyMenuItem) {
this._emptyMenuItem.hidden = false;
if (aPopup._emptyMenuItem) {
aPopup._emptyMenuItem.hidden = false;
return;
}
var label = PlacesUtils.getString("bookmarksMenuEmptyFolder");
const XULNS = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
this._emptyMenuItem = document.createElementNS(XULNS, "menuitem");
this._emptyMenuItem.setAttribute("label", label);
this._emptyMenuItem.setAttribute("disabled", true);
this.appendChild(this._emptyMenuItem);
aPopup._emptyMenuItem = document.createElement("menuitem");
aPopup._emptyMenuItem.setAttribute("label", label);
aPopup._emptyMenuItem.setAttribute("disabled", true);
aPopup.appendChild(aPopup._emptyMenuItem);
]]></body>
</method>
<method name="_rebuild">
<parameter name="aPopup"/>
<body><![CDATA[
// Make sure not to hold onto any references to menu nodes when we
// rebuild, since rebuilding deletes all the nodes in the menu and
// re-adds them. If we use a reference to a deleted node, all kinds
// of exceptions and asserts will fire.
if (this._DNDObserver._overFolder.node)
this._DNDObserver._clearOverFolder();
this._cleanMenu(aPopup);
this._cleanMenu();
NS_ASSERT(PlacesUtils.nodeIsContainer(this._resultNode),
"Result-node of a places popup has to be a container node");
#ifdef XP_MACOSX
// On Mac OSX, we need to manually attach the XBL binding for the bookmarks menu,
// because menus in the OSX menubar aren't real DOM nodes, and they don't get styles
// applied.
var currentNode = this.parentNode;
while (currentNode && !this._needsBindingAttachment) {
if (currentNode.id && currentNode.id == "bookmarksMenu")
this._needsBindingAttachment = true;
currentNode = currentNode.parentNode;
}
#endif
NS_ASSERT(this._resultNode.containerOpen,
"container must be opened when _rebuild is called");
var cc = this._resultNode.childCount;
var cc = aPopup._resultNode.childCount;
if (cc > 0) {
if (this._emptyMenuItem)
this._emptyMenuItem.hidden = true;
if (aPopup._emptyMenuItem)
aPopup._emptyMenuItem.hidden = true;
for (var i = 0; i < cc; ++i) {
var child = this._resultNode.getChild(i);
this.insertNewItem(child, null);
var child = aPopup._resultNode.getChild(i);
this.insertNewItem(child, aPopup, null);
}
}
else {
// This menu is empty. If there is no static content, add
// an element to show it is empty.
if (this._startMarker == -1 && this._endMarker == -1)
this._showEmptyMenuItem();
if (aPopup._startMarker == -1 && aPopup._endMarker == -1)
this._showEmptyMenuItem(aPopup);
}
this._built = true;
aPopup._built = true;
]]></body>
</method>
@ -348,72 +246,60 @@
<field name="_viewer"><![CDATA[({
_self: this,
_forwardToChildView:
function PMV__forwardToChildView(aNode, aFunction, aArguments) {
_getPopupForContainer:
function PMV__getPopupForContainer(aNode) {
if (this._self._resultNode == aNode)
return this._self;
for (var i=0; i < this._self._containerNodesMap.length; i++) {
if (this._self._containerNodesMap[i].resultNode == aNode) {
var childView = this._self._containerNodesMap[i].domNode._viewer;
childView[aFunction].apply(childView, aArguments);
return;
}
if (this._self._containerNodesMap[i].resultNode == aNode)
return this._self._containerNodesMap[i].domNode;
}
throw("Container view not found");
},
itemInserted: function PMV_itemInserted(aParentNode, aNode, aIndex) {
if (!this._self._built)
var popup = this._getPopupForContainer(aParentNode);
if (!popup._built)
return;
if (aParentNode == this._self.getResultNode()) {
var index = this._self._startMarker + 1 + aIndex;
var before = this._self.childNodes[index] || null;
this._self.insertNewItem(aNode, before);
if (this._self._emptyMenuItem)
this._self._emptyMenuItem.hidden = true;
}
else
this._forwardToChildView(aParentNode, "itemInserted", arguments);
var index = popup._startMarker + 1 + aIndex;
var before = popup.childNodes[index] || null;
this._self.insertNewItem(aNode, popup, before);
if (popup._emptyMenuItem)
popup._emptyMenuItem.hidden = true;
},
itemRemoved: function PMV_itemRemoved(aParentNode, aNode, aIndex) {
if (!this._self._built)
var popup = this._getPopupForContainer(aParentNode);
if (!popup._built)
return;
if (aParentNode == this._self.getResultNode()) {
var children = this._self.childNodes;
for (var i = 0; i < children.length; i++) {
if (children[i].node == aNode) {
this._self.removeItem(children[i]);
if (!this._self.hasChildNodes() ||
(this._self.childNodes.length == 1 &&
this._self.firstChild == this._self._emptyMenuItem)) {
this._self._showEmptyMenuItem();
}
var children = popup.childNodes;
for (var i = 0; i < children.length; i++) {
if (children[i].node == aNode) {
this._self.removeItem(children[i]);
if (!popup.hasChildNodes() ||
(popup.childNodes.length == 1 &&
popup.firstChild == popup._emptyMenuItem)) {
this._self._showEmptyMenuItem(popup);
}
}
}
else
this._forwardToChildView(aParentNode, "itemRemoved", arguments);
},
itemChanged: function PMV_itemChanged(aNode) {
if (!this._self._built)
return;
// this check can be removed once we fix bug #382397
var parentNode = aNode.parent;
if (!parentNode)
return;
if (parentNode != this._self.getResultNode()) {
this._forwardToChildView(parentNode, "itemChanged", arguments);
var popup = this._getPopupForContainer(parentNode);
if (!popup._built)
return;
}
var children = popup.childNodes;
var menuitem;
var children = this._self.childNodes;
for (var i = 0; i < children.length; i++) {
if (children[i].node == aNode) {
menuitem = children[i];
@ -421,58 +307,40 @@
}
}
NS_ASSERT(menuitem, "unable to find menuitem");
if (!menuitem)
return;
var title = aNode.title;
if (PlacesUtils.nodeIsSeparator(aNode)) {
// nothing to do when a separator changes
return;
}
else if (PlacesUtils.nodeIsContainer(aNode)) {
if (PlacesUtils.nodeIsLivemarkContainer(aNode)) {
var folder = aNode.itemId;
var siteURIString = PlacesUtils.livemarks.getSiteURI(folder);
if (siteURIString) {
if (menuitem.getAttribute("siteURI") != siteURIString)
menuitem.setAttribute("siteURI", siteURIString);
}
else
menuitem.removeAttribute("siteURI");
}
}
if (aNode.icon) {
if (menuitem.getAttribute("image") != aNode.icon.spec)
menuitem.setAttribute("image", aNode.icon.spec);
var iconURI = aNode.icon;
if (iconURI) {
var spec = iconURI.spec;
if (menuitem.getAttribute("image") != spec)
menuitem.setAttribute("image", spec);
}
else
menuitem.removeAttribute("image");
var title = aNode.title;
if (menuitem.getAttribute("label") != title)
menuitem.setAttribute("label", title);
},
itemReplaced:
function PMV_itemReplaced(aParentNode, aOldNode, aNewNode, aIndex) {
if (!this._self._built)
var popup = this._getPopupForContainer(aParentNode);
if (!popup._built)
return;
if (aParentNode == this._self.getResultNode()) {
var children = this._self.childNodes;
for (var i = 0; i < children.length; i++) {
if (children[i].node == aOldNode) {
var next = children[i].nextSibling;
this._self.removeItem(children[i]);
this._self.insertNewItem(aNewNode, next);
return;
}
var children = popup.childNodes;
for (var i = 0; i < children.length; i++) {
if (children[i].node == aOldNode) {
var next = children[i].nextSibling;
this._self.removeItem(children[i]);
this._self.insertNewItem(aNewNode, popup, next);
return;
}
}
else
this._forwardToChildView(aParentNode, "itemReplaced", arguments);
},
containerOpened: function PMV_containerOpened(aNode) {
@ -483,18 +351,7 @@
this.invalidateContainer(aNode);
},
get ignoreInvalidateContainer() {
return this._self._ignoreInvalidateContainer;
},
set ignoreInvalidateContainer(val) {
return this._self._ignoreInvalidateContainer = val;
},
invalidateContainer: function PMV_invalidateContainer(aContainer) {
if (this._self_ignoreInvalidateContainer)
return;
if (!this._self._built)
return;
@ -508,22 +365,22 @@
return false;
}
var viewerToRebuild = null;
var popupToRebuild = null;
for (var i=0; i < this._self._containerNodesMap.length; i++) {
var node = this._self._containerNodesMap[i].resultNode;
if (node == aContainer)
viewerToRebuild = this._self._containerNodesMap[i].domNode._viewer;
if (isChildOf(node, aContainer))
popupToRebuild = this._self._containerNodesMap[i].domNode;
if (isChildOf(node, aContainer)) {
this._self._containerNodesMap.splice(i,1);
i--;
}
}
if (aContainer.containerOpen) {
if (viewerToRebuild)
viewerToRebuild._built = false;
else
this._self._built = false;
}
if (popupToRebuild)
popupToRebuild._built = false;
else
this._self._built = false;
},
invalidateAll: function PMV_invalidateAll() {
@ -535,21 +392,6 @@
}
})]]></field>
<!-- Sometimes calling hidePopup() on a menu can leave submenus
open. This calls hidePopup() on the menu and recursively
hides its submenus as well. -->
<method name="hidePopupAndChildPopups">
<body><![CDATA[
for (var i = 0; i < this.childNodes.length; i++) {
if (this.childNodes[i].getAttribute("type") == "menu" &&
this.childNodes[i].lastChild &&
this.childNodes[i].lastChild.getAttribute("type") == "places")
this.childNodes[i].lastChild.hidePopupAndChildPopups();
}
this.hidePopup();
]]></body>
</method>
<!-- nsIPlacesView -->
<property name="place">
<getter><![CDATA[
@ -655,6 +497,7 @@
} else {
// If there is another type of node selected, the insertion point
// is after that node.
folderId = this.selectedNode.parent.itemId;
index = PlacesUtils.getIndexOfNode(this.selectedNode)
}
}
@ -686,241 +529,6 @@
]]></body>
</method>
<field name="_DNDObserver"><![CDATA[({
// Inside the _DNDObserver object's functions, this points to
// the _DNDObserver object. _self points to the menu xbl object.
_self: this,
// Subfolders should be opened when the mouse drags over them, and closed
// when the mouse drags off. The overFolder object manages opening and closing
// of folders when the mouse hovers.
_overFolder: {node: null, openTimer: null, hoverTime: 350, closeTimer: null},
// If this menu's parent auto-opened it because it was dragged over, but didn't
// close it because the mouse dragged into it, the menu should close itself
// onDragExit. This timer is set in dragExit to close the menu.
_closeMenuTimer: null,
_setTimer: function TBV_DO_setTimer(time) {
var timer = Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer);
timer.initWithCallback(this, time, timer.TYPE_ONE_SHOT);
return timer;
},
// Function to process all timer notifications.
notify: function TBV_DO_notify(timer) {
// Timer to open a submenu that's being dragged over.
if (timer == this._overFolder.openTimer) {
this._overFolder.node.lastChild.setAttribute("autoopened", "true");
this._overFolder.node.lastChild.showPopup(this._overFolder.node);
this._overFolder.openTimer = null;
}
// Timer to close a submenu that's been dragged off of.
if (timer == this._overFolder.closeTimer) {
// Only close the submenu if the mouse isn't being dragged over any
// of its child menus.
var draggingOverChild =
PlacesControllerDragHelper.draggingOverChildNode(this._overFolder.node);
if (draggingOverChild)
this._overFolder.node = null;
this._clearOverFolder();
// Close any parent folders which aren't being dragged over.
// (This is necessary because of the above code that keeps a folder
// open while its children are being dragged over.)
if (!draggingOverChild)
this._closeParentMenus();
}
// Timer to close this menu after the drag exit.
if (timer == this._closeMenuTimer) {
if (!PlacesControllerDragHelper.draggingOverChildNode(this._self)) {
this._self.hidePopupAndChildPopups();
// Close any parent menus that aren't being dragged over;
// otherwise they'll stay open because they couldn't close
// while this menu was being dragged over.
this._closeParentMenus();
}
}
},
// Helper function to close all parent menus of this menu,
// as long as none of the parent's children are currently being
// dragged over.
_closeParentMenus: function TBV_DO_closeParentMenus() {
var parent = this._self.parentNode;
while(parent) {
if (parent.nodeName == "menupopup" &&
parent.getAttribute("type") == "places") {
if (PlacesControllerDragHelper.draggingOverChildNode(parent.parentNode))
break;
parent.hidePopup();
}
parent = parent.parentNode;
}
},
// The mouse is no longer dragging over the stored menubutton.
// Close the menubutton, clear out drag styles, and clear all
// timers for opening/closing it.
_clearOverFolder: function TBV_DO_clearOverFolder() {
if (this._overFolder.node && this._overFolder.node.lastChild) {
if (!this._overFolder.node.lastChild.hasAttribute("dragover"))
this._overFolder.node.lastChild.hidePopupAndChildPopups();
this._overFolder.node = null;
}
if (this._overFolder.openTimer) {
this._overFolder.openTimer.cancel();
this._overFolder.openTimer = null;
}
if (this._overFolder.closeTimer) {
this._overFolder.closeTimer.cancel();
this._overFolder.closeTimer = null;
}
},
// This function returns information about where to drop when
// dragging over this menu--insertion point, child index to drop
// before, and folder to drop into.
_getDropPoint: function TBV_DO_getDropPoint(event) {
// Can't drop if the menu isn't a folder
var resultNode = this._self._resultNode;
if (!PlacesUtils.nodeIsFolder(this._self._result.root) ||
!PlacesUtils.nodeIsFolder(resultNode))
return null;
var dropPoint = { ip: null, beforeIndex: null, folderNode: null };
// Loop through all the nodes to see which one this should
// get dropped in/above/below.
// Ignore static content at the top and bottom of the menu.
var start = (this._self._startMarker != -1) ? (this._self._startMarker + 1) : 0;
var end = (this._self._endMarker != -1) ? this._self._endMarker : this._self.childNodes.length;
for (var i = start; i < end; i++) {
var xulNode = this._self.childNodes[i];
var nodeY = xulNode.boxObject.y - this._self.boxObject.y;
var nodeHeight = xulNode.boxObject.height;
if (xulNode.node &&
PlacesUtils.nodeIsFolder(xulNode.node) &&
!PlacesUtils.nodeIsReadOnly(xulNode.node)) {
// This is a folder. If the mouse is in the top 25% of the
// node, drop above the folder. If it's in the middle
// 50%, drop into the folder. If it's past that, drop below.
if (event.clientY < nodeY + (nodeHeight * 0.25)) {
// Drop above this folder.
dropPoint.ip = new InsertionPoint(resultNode.itemId, i - start,
-1);
dropPoint.beforeIndex = i;
return dropPoint;
}
else if (event.clientY < nodeY + (nodeHeight * 0.75)) {
// Drop inside this folder.
dropPoint.ip = new InsertionPoint(xulNode.node.itemId, -1, 1);
dropPoint.beforeIndex = i;
dropPoint.folderNode = xulNode;
return dropPoint;
}
} else {
// This is a non-folder node. If the mouse is above the middle,
// drop above the folder. Otherwise, drop below.
if (event.clientY < nodeY + (nodeHeight / 2)) {
// Drop above this bookmark.
dropPoint.ip = new InsertionPoint(resultNode.itemId, i - start, -1);
dropPoint.beforeIndex = i;
return dropPoint;
}
}
}
// Should drop below the last node.
dropPoint.ip = new InsertionPoint(resultNode.itemId, -1, 1);
dropPoint.beforeIndex = -1;
return dropPoint;
},
// This function clears all of the dragover styles that were set when
// a menuitem was dragged over.
_clearStyles: function TBV_DO_clearStyles() {
this._self.removeAttribute("dragover");
for (var i = 0; i < this._self.childNodes.length; i++) {
this._self.childNodes[i].removeAttribute("dragover-top");
this._self.childNodes[i].removeAttribute("dragover-bottom");
this._self.childNodes[i].removeAttribute("dragover-into");
}
},
onDragStart: function TBV_DO_onDragStart(event, xferData, dragAction) {
this._self._selection = event.target.node;
this._self._cachedInsertionPoint = undefined;
if (event.ctrlKey)
dragAction.action = Ci.nsIDragService.DRAGDROP_ACTION_COPY;
xferData.data = this._self._controller.getTransferData(dragAction.action);
},
canDrop: function TBV_DO_canDrop(event, session) {
return PlacesControllerDragHelper.canDrop(this._self, -1);
},
onDragOver: function TBV_DO_onDragOver(event, flavor, session) {
PlacesControllerDragHelper.currentDropTarget = event.target;
var dropPoint = this._getDropPoint(event);
if (dropPoint == null)
return;
this._clearStyles();
if (dropPoint.folderNode) {
// Dragging over a folder; set the appropriate styles.
if (this._overFolder.node != dropPoint.folderNode) {
this._clearOverFolder();
this._overFolder.node = dropPoint.folderNode;
this._overFolder.openTimer = this._setTimer(this._overFolder.hoverTime);
}
dropPoint.folderNode.setAttribute("dragover-into", "true");
}
else {
// Dragging over a menuitem, set dragover-top/bottom to show where
// the item will be dropped and clear out any old folder info.
if (dropPoint.beforeIndex == -1) {
if (this._self.endMatch)
this._self.childNodes[this._self.endMatch].setAttribute("dragover-top", "true");
else
this._self.lastChild.setAttribute("dragover-bottom", "true");
}
else {
this._self.childNodes[dropPoint.beforeIndex].setAttribute("dragover-top", "true");
}
// Clear out old folder information
this._clearOverFolder();
}
this._self.setAttribute("dragover", "true");
},
onDrop: function TBV_DO_onDrop(event, dropData, session) {
var dropPoint = this._getDropPoint(event);
if (dropPoint == null)
return;
PlacesControllerDragHelper.onDrop(null, this._self, dropPoint.ip);
},
onDragExit: function TBV_DO_onDragExit(event, session) {
PlacesControllerDragHelper.currentDropTarget = null;
this._clearStyles();
// Close any folder being hovered over
if (this._overFolder.node)
this._overFolder.closeTimer = this._setTimer(this._overFolder.hoverTime);
// The autoopened attribute is set when this folder was automatically
// opened after the user dragged over it. If this attribute is set,
// auto-close the folder on drag exit.
if (this._self.hasAttribute("autoopened"))
this._closeMenuTimer = this._setTimer(this._overFolder.hoverTime);
},
getSupportedFlavours: function TBV_DO_getSupportedFlavours() {
var flavorSet = new FlavourSet();
for (var i = 0; i < this._self.peerDropTypes.length; ++i)
flavorSet.appendFlavour(this._self.peerDropTypes[i]);
return flavorSet;
}
})]]></field>
<property name="selType" readonly="true" onget="return 'single';"/>
<method name="buildContextMenu">
@ -943,64 +551,48 @@
</method>
</implementation>
<handlers>
<handler event="popupshowing">
if (event.target == this)
this.onPopupShowing();
<handler event="popupshowing" phase="capturing">
this._ensureInitialized();
if (event.target._resultNode)
this.onPopupShowing(event);
</handler>
<handler event="popuphidden">
if (event.target != this)
var popup = event.target;
if (!popup._resultNode)
return;
// UI performance: folder queries are cheap, keep the resultnode open
// so we don't rebuild its contents whenever the popup is reopened.
if (!PlacesUtils.nodeIsFolder(this._resultNode)) {
this._resultNode.containerOpen = false;
this._built = false;
}
if (!PlacesUtils.nodeIsFolder(popup._resultNode))
popup._resultNode.containerOpen = false;
// The autoopened attribute is set for folders which have been
// automatically opened when dragged over. Turn off this attribute
// when the folder closes because it is no longer applicable.
this.removeAttribute("autoopened");
popup.removeAttribute("autoopened");
</handler>
<!-- Set selected node on DOMMenuItemActive/contextmenu events
so that they're set up when command and click events fire. -->
<handler event="DOMMenuItemActive"><![CDATA[
if (event.target.parentNode == this) {
// Set the selection to the node that was activated. If that
// node has a command but no data associated with it, it should
// act on the entire menu.
// Set the selection to the node that was activated. If that
// node has a command but no data associated with it, it should
// act on the entire menu.
if (event.target.parentNode._resultNode) {
this._cachedInsertionPoint = undefined;
this._selection = event.target.node || this._resultNode;
this._selection = event.target.node ||
event.target.parentNode._resultNode;
}
]]></handler>
<handler event="contextmenu"><![CDATA[
// DOMMenuItemActive is not dispatched for disabled menuitems and
// menuseparators. Set the selection here manually.
var popupNode = document.popupNode;
// |popupNode == this| happens when the area between menuseparators
// is clicked.
if (popupNode == this || popupNode.parentNode == this) {
this._selection = popupNode.node || this._resultNode;
this._cachedInsertionPoint = undefined;
}
]]></handler>
<handler event="draggesture"><![CDATA[
if (event.target.localName == "menuitem")
// TODO--allow menu drag if shift (or alt??) key is down
nsDragAndDrop.startDrag(event, this._DNDObserver);
]]></handler>
<handler event="dragover"><![CDATA[
nsDragAndDrop.dragOver(event, this._DNDObserver);
]]></handler>
<handler event="dragdrop"><![CDATA[
nsDragAndDrop.drop(event, this._DNDObserver);
]]></handler>
<handler event="dragexit"><![CDATA[
nsDragAndDrop.dragExit(event, this._DNDObserver);
// |popupNode == menupopup| happens when the area between
// menuseparators is clicked.
this._selection = popupNode.node || popupNode.parentNode._resultNode;
this._cachedInsertionPoint = undefined;
]]></handler>
</handlers>
</binding>

Просмотреть файл

@ -52,12 +52,9 @@ var gMoveBookmarksDialog = {
this._nodes = window.arguments[0];
this._tm = window.arguments[1];
// setTimeout until bug 373944 is fixed
setTimeout(function(aSelf) {
// select and expand the root node
aSelf.foldersTree.selectFolders([PlacesUtils.bookmarksRootId]);
aSelf.foldersTree.selectedNode.containerOpen = true;
}, 0, this);
// select and expand the root node
this.foldersTree.selectFolders([PlacesUtils.bookmarksRootId]);
this.foldersTree.selectedNode.containerOpen = true;
},
onOK: function MBD_onOK(aEvent) {

Просмотреть файл

@ -54,13 +54,6 @@ var PlacesOrganizer = {
_content: null,
init: function PO_init() {
var self = this;
// on timeout because of the corresponding setTimeout()
// in the places tree binding's constructor
setTimeout(function() { self._init(); }, 0);
},
_init: function PO__init() {
this._places = document.getElementById("placesList");
this._content = document.getElementById("placeContent");
@ -576,7 +569,8 @@ var PlacesOrganizer = {
// are saved
if (gEditItemOverlay.itemId != -1) {
var focusedElement = document.commandDispatcher.focusedElement;
if (focusedElement instanceof HTMLInputElement &&
if ((focusedElement instanceof HTMLInputElement ||
focusedElement instanceof HTMLTextAreaElement) &&
/^editBMPanel.*/.test(focusedElement.parentNode.parentNode.id))
focusedElement.blur();
}

Просмотреть файл

@ -124,7 +124,7 @@
oncommand="close();"/>
<key id="placesKey_show:debug"
key="d" modifiers="accel,shift"
key="e" modifiers="accel,shift"
oncommand="PlacesOrganizer.toggleDebugPanel();"/>
<!-- Command Keys -->

Просмотреть файл

@ -54,7 +54,7 @@
<resources>
<stylesheet src="chrome://browser/skin/places/places.css"/>
</resources>
<content>
<xul:vbox>
<xul:hbox class="toolbar-drop-indicator-bar">
@ -75,9 +75,9 @@
<xul:toolbarbutton type="menu"
class="chevron"
mousethrough="never"
collapsed="true">
<xul:menupopup type="places"
anonid="chevronPopup"
collapsed="true"
onpopupshowing="chevronPopupShowing(event);">
<xul:menupopup anonid="chevronPopup"
#ifndef XP_MACOSX
context="placesContext"
#endif
@ -85,26 +85,17 @@
</xul:toolbarbutton>
</xul:hbox>
</content>
<implementation>
<constructor><![CDATA[
// Support an asyncinit attribute that causes the view to populate
// itself only after the window has been shown. This is to ensure we
// do not regress browser window show time (Ts/Txul)
#if 0
if (this.hasAttribute("asyncinit")) {
var self = this;
//setTimeout(function() { self._init(); }, 0);
}
else
#endif
this._init();
this._init();
]]></constructor>
<destructor><![CDATA[
PlacesUtils.annotations.removeObserver(this.genericAnnoObserver);
this._result.viewer = null;
this._result = null;
<destructor><![CDATA[
if (this._result) {
this._result.viewer = null;
this._result = null;
}
]]></destructor>
<property name="controller"
@ -121,8 +112,6 @@
function f(e) { t.updateChevron(e); },
false);
PlacesUtils.annotations.addObserver(this.genericAnnoObserver);
if (this.hasAttribute("place")) {
// Do the initial build.
this.place = this.place;
@ -132,14 +121,12 @@
<field name="_dropIndicatorBar">document.getAnonymousElementByAttribute(this, "class", "toolbar-drop-indicator-bar")</field>
<field name="_chevron">document.getAnonymousElementByAttribute(this, "class", "chevron")</field>
<field name="_selection">null</field>
<field name="_openedMenuButton">null</field>
<field name="_result">null</field>
<field name="_ignoreInvalidateContainer">false</field>
<field name="_selection">null</field>
<field name="_openedMenuButton">null</field>
<field name="_result">null</field>
<!-- nsIPlacesView -->
<method name="getResult">
@ -164,85 +151,69 @@
while (this.hasChildNodes())
this.removeChild(this.firstChild);
const XULNS = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
var cc = this._result.root.childCount;
for (var i = 0; i < cc; ++i)
this.insertNewItem(this._result.root.getChild(i), null);
var popup = this._chevron.firstChild;
popup.setAttribute("type", "places");
// This is set here and not in the XBL constructor for the menu because
// it doesn't get initialized properly in the constructor.
#ifndef XP_MACOSX
// No context menus on menuitems on Mac
popup.setAttribute("context", "placesContext");
#endif
popup.place = this.place;
var t = this;
popup.popupShowingCallback = function() { t.chevronPopupShowing(); };
var rootNode = this._result.root;
var cc = rootNode.childCount;
for (var i = 0; i < cc; ++i)
this.insertNewItem(rootNode.getChild(i), null);
var chevronPopup = this._chevron.lastChild;
if (chevronPopup.hasAttribute("type")) {
// Otherwise we'll set it when the chevron is enabled (see updateChevron)
chevronPopup.place = this.place;
}
while (chevronPopup.hasChildNodes())
chevronPopup.removeChild(chevronPopup.lastChild);
// This needs to be in a timeout to make sure our boxObject has time
// to get its proper size
var t = this;
setTimeout(function() { t.updateChevron(); }, 0);
]]></body>
</method>
<method name="insertNewItem">
<parameter name="child"/>
<parameter name="before"/>
<parameter name="aChild"/>
<parameter name="aBefore"/>
<body><![CDATA[
const XULNS = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
var title = child.title;
var button = null;
if (PlacesUtils.nodeIsURI(child)) {
button = document.createElementNS(XULNS, "toolbarbutton");
} else if (PlacesUtils.nodeIsSeparator(child)) {
button = document.createElementNS(XULNS, "toolbarseparator");
} else if (PlacesUtils.nodeIsContainer(child)) {
button = document.createElementNS(XULNS, "toolbarbutton");
button.setAttribute("type", "menu");
button.setAttribute("container", "true");
if (PlacesUtils.nodeIsLivemarkContainer(child)) {
button.setAttribute("livemark", "true");
var folder = child.itemId;
// duplicate nsLivemarkService.getSiteURI to avoid instantiating
// the service on startup.
var siteURIString;
try {
siteURIString =
PlacesUtils.annotations.getItemAnnotation(folder, "livemark/siteURI");
}
catch (ex) {}
// end duplication
if (siteURIString)
button.setAttribute("siteURI", siteURIString);
var type = aChild.type;
var button;
if (type == Ci.nsINavHistoryResultNode.RESULT_TYPE_SEPARATOR)
button = document.createElement("toolbarseparator");
else {
button = document.createElement("toolbarbutton");
button.className = "bookmark-item";
button.setAttribute("label", aChild.title);
var iconURI = aChild.icon;
var iconURISpec = "";
if (iconURI) {
iconURISpec = iconURI.spec;
button.setAttribute("image", iconURISpec);
}
var popup = document.createElementNS(XULNS, "menupopup");
popup.setAttribute("type", "places");
// This is set here and not in the XBL constructor for the menu because
// it doesn't get initialized properly in the constructor.
if (PlacesUtils.containerTypes.indexOf(type) != -1) {
button.setAttribute("type", "menu");
button.setAttribute("container", "true");
if (iconURISpec == "chrome://browser/skin/places/livemarkItem.png")
button.setAttribute("livemark", "true");
var popup = document.createElement("menupopup");
button.appendChild(popup);
popup._result = this._result;
popup._resultNode = asContainer(aChild);
#ifndef XP_MACOSX
// No context menus on menuitems on Mac
popup.setAttribute("context", "placesContext");
popup.setAttribute("context", "placesContext");
#endif
button.appendChild(popup);
popup._result = this._result;
popup._resultNode = asContainer(child);
popup._containerNodesMap = this._containerNodesMap;
this._containerNodesMap.push({ resultNode: child,
domNode: popup });
this._containerNodesMap.push({ resultNode: aChild,
domNode: popup });
}
}
button.setAttribute("label", title);
if (child.icon)
button.setAttribute("image", child.icon.spec);
button.className = "menuitem-iconic bookmark-item";
button.node = child;
button.node = aChild;
button.node.viewIndex = 0;
if (before)
this.insertBefore(button, before);
if (aBefore)
this.insertBefore(button, aBefore);
else
this.appendChild(button);
]]></body>
@ -253,18 +224,24 @@
<body><![CDATA[
if (PlacesUtils.nodeIsContainer(child.node)) {
for (var i=0; i < this._containerNodesMap.length; i++) {
if (this._containerNodesMap[i].resultNode == child.node)
if (this._containerNodesMap[i].resultNode == child.node) {
this._containerNodesMap.splice(i, 1);
break;
}
}
}
this.removeChild(child);
child.parentNode.removeChild(child);
]]></body>
</method>
<method name="chevronPopupShowing">
<parameter name="aEvent"/>
<body><![CDATA[
var popup = this._chevron.firstChild;
var popup = aEvent.target;
if (popup != this._chevron.firstChild)
return;
for (var i = 0; i < popup.childNodes.length; i++)
popup.childNodes[i].hidden = !this.childNodes[i].collapsed;
]]></body>
@ -281,7 +258,7 @@
return element.boxObject.width + leftMargin + rightMargin;
]]></body>
</method>
<method name="updateChevron">
<parameter name="event"/>
<body><![CDATA[
@ -312,10 +289,17 @@
child.collapsed = true;
}
}
this._chevron.collapsed = !overflowed;
if (!(this._chevron.collapsed = !overflowed)) {
// Attach the popup binding to the chevron popup
var popup = this._chevron.firstChild;
if (!popup.hasAttribute("type")) {
popup.setAttribute("place", this.place);
popup.setAttribute("type", "places");
}
}
]]></body>
</method>
<!-- nsIPlacesView -->
<property name="place">
<getter><![CDATA[
@ -414,7 +398,7 @@
var folderId = this._result.root.itemId;
if (this.hasSelection) {
if(PlacesUtils.nodeIsFolder(this.selectedNode)) {
if (PlacesUtils.nodeIsFolder(this.selectedNode)) {
// If there is a folder selected, the insertion point is the
// end of the folder.
folderId = this.selectedNode.itemId;
@ -442,23 +426,21 @@
]]></body>
</method>
<!-- Map for containerNodes<->domNodes. There's only one map per
result/viewer, i.e. the field is initialized just for the toolbar,
for sub menus it is set to the root's map -->
<!-- Map for containerNodes<->domNodes. -->
<field name="_containerNodesMap">[]</field>
<!-- nsINavHistoryResultViewer -->
<field name="_viewer"><![CDATA[({
_self: this,
_forwardToChildView:
function TV_V__forwardToChildView(aNode, aFunction, aArguments) {
_getPopupForContainer:
function PMV__getPopupForContainer(aNode) {
if (this._self._resultNode == aNode)
return this._self;
for (var i=0; i < this._self._containerNodesMap.length; i++) {
if (this._self._containerNodesMap[i].resultNode == aNode) {
var childView = this._self._containerNodesMap[i].domNode._viewer;
childView[aFunction].apply(childView, aArguments);
return;
}
if (this._self._containerNodesMap[i].resultNode == aNode)
return this._self._containerNodesMap[i].domNode;
}
throw("Container view not found");
},
@ -466,19 +448,26 @@
itemInserted: function TV_V_itemInserted(aParentNode, aNode, aIndex) {
// don't insert new items into the toolbar
// if the parent is not the root
if (aParentNode == this._self.getResult().root) {
if (aParentNode == this._self.getResultNode()) {
var children = this._self.childNodes;
this._self.insertNewItem(aNode,
aIndex < children.length ? children[aIndex] : null);
this._self.updateChevron();
}
else {
this._forwardToChildView(aParentNode, "itemInserted", arguments);
var popup = this._getPopupForContainer(aParentNode);
if (!popup._built)
return;
var before = popup.childNodes[aIndex] || null;
this._self.insertNewItemToPopup(aNode, popup, before);
if (popup._emptyMenuItem)
popup._emptyMenuItem.hidden = true;
}
},
itemRemoved: function TV_V_itemRemoved(aParentNode, aNode, aIndex) {
if (aParentNode == this._self.getResult().root) {
if (aParentNode == this._self.getResultNode()) {
var children = this._self.childNodes;
for (var i = 0; i < children.length; i++) {
if (children[i].node == aNode) {
@ -488,8 +477,23 @@
}
}
}
else
this._forwardToChildView(aParentNode, "itemRemoved", arguments);
else {
var popup = this._getPopupForContainer(aParentNode);
if (!popup._built)
return;
var children = popup.childNodes;
for (var i = 0; i < children.length; i++) {
if (children[i].node == aNode) {
this._self.removeItem(children[i]);
if (!popup.hasChildNodes() ||
(popup.childNodes.length == 1 &&
popup.firstChild == popup._emptyMenuItem)) {
this._self._showEmptyMenuItem(popup);
}
}
}
}
},
itemChanged: function TV_V_itemChanged(aNode) {
@ -498,63 +502,57 @@
if (!parentNode)
return;
if (parentNode != this._self.getResult().root) {
this._forwardToChildView(parentNode, "itemChanged", arguments);
return;
}
var button;
var children = this._self.childNodes;
for (var i = 0; i < children.length; i++) {
if (children[i].node == aNode) {
button = children[i];
break;
var element;
var onToolbar = false;
if (parentNode == this._self.getResultNode()) {
onToolbar = true;
var children = this._self.childNodes;
for (var i = 0; i < children.length; i++) {
if (children[i].node == aNode) {
element = children[i];
break;
}
}
}
else {
var popup = this._getPopupForContainer(parentNode);
if (!popup._built)
return;
NS_ASSERT(button, "unable to find a toolbar element");
var title = aNode.title;
var children = popup.childNodes;
for (var i = 0; i < children.length; i++) {
if (children[i].node == aNode) {
element = children[i];
break;
}
}
}
if (PlacesUtils.nodeIsSeparator(aNode)) {
// nothing to do when a separator changes
return;
}
else if (PlacesUtils.nodeIsContainer(aNode)) {
if (PlacesUtils.nodeIsLivemarkContainer(aNode)) {
var folder = aNode.itemId;
var siteURIString = "";
var siteURI = PlacesUtils.livemarks.getSiteURI(folder);
if (siteURI)
siteURIString = siteURI.spec;
if (siteURIString) {
if (button.getAttribute("siteURI") != siteURIString)
button.setAttribute("siteURI", siteURIString);
}
else
button.removeAttribute("siteURI");
}
}
if (aNode.icon) {
if (button.getAttribute("image") != aNode.icon.spec)
button.setAttribute("image", aNode.icon.spec);
var iconURI = aNode.icon;
if (iconURI) {
var spec = iconURI.spec;
if (element.getAttribute("image") != spec)
element.setAttribute("image", spec);
}
else
button.removeAttribute("image");
// the only change that might require a chevron update
// is when the title changes
if (button.getAttribute("label") != title) {
button.setAttribute("label", title);
this._self.updateChevron();
element.removeAttribute("image");
var title = aNode.title;
if (element.getAttribute("label") != title) {
element.setAttribute("label", title);
if (onToolbar)
this._self.updateChevron();
}
},
itemReplaced:
function TV_V_itemReplaced(aParentNode, aOldNode, aNewNode, aIndex) {
if (aParentNode == this._self.getResult().root) {
if (aParentNode == this._self.getResultNode()) {
var children = this._self.childNodes;
for (var i = 0; i < children.length; i++) {
if (children[i].node == aOldNode) {
@ -578,17 +576,12 @@
this.invalidateContainer(aNode);
},
get ignoreInvalidateContainer() {
return this._self._ignoreInvalidateContainer;
},
set ignoreInvalidateContainer(val) {
return this._self._ignoreInvalidateContainer = val;
},
invalidateContainer: function TV_V_invalidateContainer(aContainer) {
if (this._self._ignoreInvalidateContainer)
if (aContainer == this._self.getResultNode()) {
this._self._containerNodesMap.splice(0);
this._self._rebuild();
return;
}
function isChildOf(node, container) {
var parent = node.parent;
@ -600,22 +593,20 @@
return false;
}
var viewerToRebuild = null;
var popupToRebuild = null;
for (var i=0; i < this._self._containerNodesMap.length; i++) {
var node = this._self._containerNodesMap[i].resultNode;
if (node == aContainer)
viewerToRebuild = this._self._containerNodesMap[i].domNode._viewer;
if (isChildOf(node, aContainer))
popupToRebuild = this._self._containerNodesMap[i].domNode;
if (isChildOf(node, aContainer)) {
this._self._containerNodesMap.splice(i,1);
i--;
}
}
if (aContainer.containerOpen) {
if (viewerToRebuild)
viewerToRebuild._self._built = false;
else
this._self._rebuild();
}
if (popupToRebuild)
popupToRebuild._built = false;
},
invalidateAll: function TV_V_invalidateAll() {
@ -639,22 +630,21 @@
// timer for turning of indicator bar, to get rid of flicker
_ibTimer: null,
_setTimer: function TBV_DO_setTimer(time) {
var timer = Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer);
timer.initWithCallback(this, time, timer.TYPE_ONE_SHOT);
return timer;
},
// Function to process all timer notifications.
notify: function TBV_DO_notify(timer) {
// Timer to turn off indicator bar.
if (timer == this._ibTimer) {
ib = this._self._dropIndicatorBar.removeAttribute('dragging');
this._ibTimer = null;
}
// Timer to open a menubutton that's being dragged over.
if (timer == this._overFolder.openTimer) {
// Set the autoopen attribute on the folder's menupopup so that
@ -694,7 +684,7 @@
_clearOverFolder: function TBV_DO_clearOverFolder() {
if (this._overFolder.node && this._overFolder.node.lastChild) {
if (!this._overFolder.node.lastChild.hasAttribute("dragover")) {
this._overFolder.node.lastChild.hidePopupAndChildPopups();
this._overFolder.node.lastChild.hidePopup();
}
this._overFolder.node.removeAttribute("dragover");
this._overFolder.node = null;
@ -835,14 +825,14 @@
this._clearOverFolder();
}
},
onDrop: function TBV_DO_onDrop(event, dropData, session) {
var dropPoint = this._getDropPoint(event);
if (dropPoint == null)
return;
PlacesControllerDragHelper.onDrop(null, this._self, dropPoint.ip);
},
onDragExit: function TBV_DO_onDragExit(event, session) {
// Set timer to turn off indicator bar (if we turn it off
// here, dragenter might be called immediately after, creating
@ -855,103 +845,15 @@
this._overFolder.closeTimer = this._setTimer(this._overFolder.hoverTime);
PlacesControllerDragHelper.currentDropTarget = null;
},
getSupportedFlavours: function TBV_DO_getSupportedFlavours() {
var flavorSet = new FlavourSet();
for (var i = 0; i < this._self.peerDropTypes.length; ++i)
flavorSet.appendFlavour(this._self.peerDropTypes[i]);
return flavorSet;
}
})]]></field>
<!-- nsIAnnotationObserver -->
<field name="genericAnnoObserver"><![CDATA[({
// A generic nsIAnnotationObserver that provides methods for registering
// annotation-specific observers for this view.
// Inside this observer object's functions, "this" points to this
// observer object, while "_self" points to the toolbar XBL object.
_self: this,
// Observers, indexed by annotation name.
_observers: {},
addObserver: function TBV_GAO_addObserver(annoName, observer) {
if (!this._observers[annoName])
this._observers[annoName] = [];
// Register the observer, but only if it isn't already registered,
// so that we don't call the same observer twice for any given change.
if (this._observers[annoName].indexOf(observer) == -1)
this._observers[annoName].push(observer);
},
removeObserver: function TBV_GAO_removeObserver(annoName, observer) {
NS_ASSERT(this._observers[annoName] &&
this._observers[annoName].indexOf(observer) != -1,
"can't remove annotation observer " + observer +
" for annotation " + annoName + ": not registered");
this._observers[annoName] =
this._observers[annoName].filter(function(i) { observer != i });
if (this._observers[annoName].length == 0)
delete this._observers[annoName];
},
// Determines whether or not a given annotation change applies to
// this view. A change applies if the annotation being changed is one
// we're observing, and the change is happening to a URI currently
// in this view.
_applies: function TBV_GAO_applies(uri, annoName) {
if (!this._observers[annoName])
return false;
return true;
},
onPageAnnotationSet:
function TBV_GAO_onPageAnnotationSet(uri, annoName) {
if (!this._applies(uri, annoName))
return;
for (var i = 0; i < this._observers[annoName].length; i++)
this._observers[annoName][i].onPageAnnotationSet(uri, annoName);
},
onPageAnnotationRemoved:
function TBV_GAO_onPageAnnotationRemoved(uri, annoName) {
if (!this._applies(uri, annoName))
return;
for ( var i = 0; i < this._observers[annoName].length; i++)
this._observers[annoName][i].onPageAnnotationRemoved(uri, annoName);
},
onItemAnnotationSet:
function TBV_GAO_onItemAnnotationSet(aItemId, aAnnoName) {
if (!this._applies(aItemId, aAnnoName))
return;
for (var i = 0; i < this._observers[aAnnoName].length; i++) {
this._observers[aAnnoName][i]
.onItemAnnotationSet(aItemId, aAnnoName);
}
},
onItemAnnotationRemoved:
function TBV_GAO_onItemAnnotationRemoved(aItemId, aAnnoName) {
if (!this._applies(aItemId, aAnnoName))
return;
for (var i = 0; i < this._observers[aAnnoName].length; i++) {
this._observers[aAnnoName][i]
.onItemAnnotationRemoved(aItemId, aAnnoName);
}
}
})]]></field>
<method name="checkForMenuEvent">
<parameter name="event"/>
<parameter name="action"/>
@ -998,21 +900,111 @@
<method name="destroyContextMenu">
<parameter name="aPopup"/>
<body>
<![CDATA[
if (window.content)
window.content.focus();
]]>
</body>
<body><![CDATA[
if (window.content)
window.content.focus();
]]></body>
</method>
<method name="_showEmptyMenuItem">
<parameter name="aPopup"/>
<body><![CDATA[
if (aPopup._emptyMenuItem) {
aPopup._emptyMenuItem.hidden = false;
return;
}
var label = PlacesUtils.getString("bookmarksMenuEmptyFolder");
aPopup._emptyMenuItem = document.createElement("menuitem");
aPopup._emptyMenuItem.setAttribute("label", label);
aPopup._emptyMenuItem.setAttribute("disabled", true);
aPopup.appendChild(aPopup._emptyMenuItem);
]]></body>
</method>
<method name="insertNewItemToPopup">
<parameter name="aChild"/>
<parameter name="aParentPopup"/>
<parameter name="aBefore"/>
<body><![CDATA[
var element =
PlacesUtils.createMenuItemForNode(aChild, this._containerNodesMap);
if (aBefore)
aParentPopup.insertBefore(element, aBefore);
else
aParentPopup.appendChild(element);
]]></body>
</method>
<method name="_containerPopupShowing">
<parameter name="aPopup"/>
<body><![CDATA[
if (aPopup._built)
return;
// remove previous menu items
while (aPopup.hasChildNodes())
aPopup.removeChild(aPopup.firstChild);
// restore the empty-menu item if has been created already
if (aPopup._emptyMenuItem)
aPopup.appendChild(aPopup._emptyMenuItem);
var resultNode = aPopup._resultNode;
if (!resultNode.containerOpen)
resultNode.containerOpen = true;
var cc = resultNode.childCount;
if (cc > 0) {
if (aPopup._emptyMenuItem)
aPopup._emptyMenuItem.hidden = true;
for (var i = 0; i < cc; ++i) {
var child = resultNode.getChild(i);
this.insertNewItemToPopup(child, aPopup, null);
}
}
else {
// add element to show it is empty.
this._showEmptyMenuItem(aPopup);
}
aPopup._built = true;
if (!aPopup._DNDObserver)
aPopup._DNDObserver = new PlacesMenuDNDObserver(this, aPopup);
]]></body>
</method>
<method name="_isChevronChild">
<parameter name="aChild"/>
<body><![CDATA[
if (!this._chevron.firstChild.hasAttribute("type"))
return false;
var parent = aChild.parentNode;
while (parent != this) {
if (parent == this._chevron)
return true;
parent = parent.parentNode;
}
return false;
]]></body>
</method>
</implementation>
<handlers>
<handler event="mousedown"><![CDATA[
// When the user clicks down on a button, set it as the selection and
// tell the controller that we are the active view.
if (event.target.localName == "toolbarbutton" ||
event.target.localName == "toolbarseparator")
this._selection = event.target.node;
//
// Sub-menus are handled by the DOMMenuItemActive handler
var target = event.target;
if (target.parentNode != this)
return;
if (target.localName == "toolbarbutton" ||
target.localName == "toolbarseparator")
this._selection = target.node;
else
this._selection = this.getResult().root;
this._cachedInsertionPoint = undefined;
@ -1033,22 +1025,74 @@
if (!this.checkForMenuEvent(event, "dragExit"))
nsDragAndDrop.dragExit(event, this._DNDObserver);
]]></handler>
<handler event="popupshowing"><![CDATA[
var targetParent = event.originalTarget.parentNode;
<handler event="popupshowing" phase="capturing"><![CDATA[
var target = event.originalTarget;
// the chevron has its own view
if (this._isChevronChild(target))
return;
if (target._resultNode)
this._containerPopupShowing(target);
var targetParent = target.parentNode;
if (targetParent.localName == "toolbarbutton" &&
!PlacesControllerDragHelper.getSession())
this._openedMenuButton = targetParent;
]]></handler>
<handler event="popuphidden"><![CDATA[
var targetParent = event.originalTarget.parentNode;
var target = event.originalTarget;
if (!target._resultNode)
return;
// the chevron has its own view
if (this._isChevronChild(target))
return;
// UI performance: folder queries are cheap, keep the resultnode open
// so we don't rebuild its contents whenever the popup is reopened.
if (!PlacesUtils.nodeIsFolder(target._resultNode))
target._resultNode.containerOpen = false;
var targetParent = target.parentNode;
if (targetParent.localName == "toolbarbutton" &&
!PlacesControllerDragHelper.getSession())
this._openedMenuButton = null;
]]></handler>
<!-- Set selected node on DOMMenuItemActive/contextmenu events
so that they're set up when command and click events fire. -->
<handler event="DOMMenuItemActive"><![CDATA[
// Set the selection to the node that was activated. If that
// node has a command but no data associated with it, it should
// act on the entire menu.
if (event.target.parentNode._resultNode) {
// the chevron has its own view
if (this._isChevronChild(event.target))
return;
this._cachedInsertionPoint = undefined;
this._selection = event.target.node ||
event.target.parentNode._resultNode;
}
]]></handler>
<handler event="contextmenu"><![CDATA[
// DOMMenuItemActive is not dispatched for disabled menuitems and
// menuseparators. Set the selection here manually.
var popupNode = document.popupNode;
// the chevron has its own view
if (this._isChevronChild(popupNode))
return;
// |popupNode == menupopup| happens when the area between menuseparators
// is clicked.
this._selection = popupNode.node || popupNode.parentNode._resultNode;
this._cachedInsertionPoint = undefined;
]]></handler>
<handler event="mousemove"><![CDATA[
if (this._openedMenuButton == null || PlacesControllerDragHelper.getSession())
return;
var target = event.originalTarget;
if (this._openedMenuButton != target &&
target.localName == "toolbarbutton" &&

Просмотреть файл

@ -49,14 +49,9 @@
this._controller = new PlacesController(this);
this.controllers.appendController(this._controller);
// Force an initial build.
// but do it on setTimeout() for bugs #373719 and bug #373721
// caused by a change for bug #267833
// note the corresponding setTimeout() in PO_init()
if (this.place) {
var self = this;
setTimeout(function() { self.place = self.place; }, 0);
}
// Force an initial build.
if (this.place)
this.place = this.place;
]]></constructor>
<destructor><![CDATA[
@ -83,11 +78,13 @@
var resultview = this.getResultView();
if (resultview)
resultview.removeViewObserver(this._viewObserver);
this.treeBoxObject.view = val;
if (val) {
val.QueryInterface(Ci.nsINavHistoryResultViewer)
.addViewObserver(this._viewObserver, false);
}
return val;
]]></setter>
</property>
@ -114,11 +111,11 @@
if (optionsFilter)
options = optionsFilter.filter(queryNode.getQueries({}), options,
optionsFilter.historyHandler);
var query = PlacesUtils.history.getNewQuery();
query.searchTerms = filterString;
query.onlyBookmarked = onlyBookmarks;
// Remove "group by folder" from the options list, because
// nsNavHistory::RecursiveGroup doesn't support it.
function isFolderGrouping(grouping, index, ary) {
@ -156,7 +153,8 @@
if (this.showRoot != val) {
this.setAttribute("showRoot", val);
// reload with the last place set
this.place = this.place;
if (this.place)
this.place = this.place;
}
return val;
]]></setter>
@ -278,7 +276,7 @@
<getter><![CDATA[
return this.getAttribute("place");
]]></getter>
<setter><![CDATA[
<setter><![CDATA[
this.setAttribute("place", val);
var queriesRef = { };

Просмотреть файл

@ -215,6 +215,7 @@ PlacesTreeView.prototype = {
var cc = aContainer.childCount;
for (var i=0; i < cc; i++) {
var curChild = aContainer.getChild(i);
var curChildType = curChild.type;
// collapse all duplicates starting from here
if (this._collapseDuplicates) {
@ -226,6 +227,7 @@ PlacesTreeView.prototype = {
// collapse the first and use the second
curChild.viewIndex = -1;
curChild = aContainer.getChild(i+1);
curChildType = curChild.type;
}
else {
// collapse the second and use the first
@ -236,7 +238,7 @@ PlacesTreeView.prototype = {
}
// don't display separators when sorted
if (PlacesUtils.nodeIsSeparator(curChild)) {
if (curChildType == Ci.nsINavHistoryResultNode.RESULT_TYPE_SEPARATOR) {
if (this._result.sortingMode !=
Ci.nsINavHistoryQueryOptions.SORT_BY_NONE) {
curChild.viewIndex = -1;
@ -249,11 +251,13 @@ PlacesTreeView.prototype = {
aVisible.push(curChild);
// recursively do containers
if (PlacesUtils.nodeIsContainer(curChild)) {
if (PlacesUtils.containerTypes.indexOf(curChildType) != -1) {
asContainer(curChild);
var resource = this._getResourceForNode(curChild);
var isopen = resource != null &&
PlacesUtils.localStore.HasAssertion(resource, openLiteral, trueLiteral, true);
asContainer(curChild);
PlacesUtils.localStore.HasAssertion(resource, openLiteral,
trueLiteral, true);
if (isopen != curChild.containerOpen)
aToOpen.push(curChild);
else if (curChild.containerOpen && curChild.childCount > 0)
@ -371,7 +375,7 @@ PlacesTreeView.prototype = {
// now, open any containers that were persisted
for (var i = 0; i < toOpenElements.length; i++) {
var item = asContainer(toOpenElements[i]);
var item = toOpenElements[i];
var parent = item.parent;
// avoid recursively opening containers
while (parent) {
@ -734,20 +738,9 @@ PlacesTreeView.prototype = {
containerClosed: function PTV_containerClosed(aItem) {
this.invalidateContainer(aItem);
},
get ignoreInvalidateContainer() {
return this._ignoreInvalidateContainer;
},
set ignoreInvalidateContainer(val) {
return this._ignoreInvalidateContainer = val;
},
invalidateContainer: function PTV_invalidateContainer(aItem) {
if (this._ignoreInvalidateContainer)
return;
invalidateContainer: function PTV_invalidateContainer(aItem) {
NS_ASSERT(this._result, "Got a notification but have no result!");
if (!this._tree)
return; // nothing to do, container is not visible
@ -808,8 +801,10 @@ PlacesTreeView.prototype = {
},
set result(val) {
this._result = val;
this._finishInit();
if (this._result != val) {
this._result = val;
this._finishInit();
}
return val;
},
@ -875,7 +870,7 @@ PlacesTreeView.prototype = {
return viewIndex;
},
_getResourceForNode : function PTV_getResourceForNode(aNode)
_getResourceForNode: function PTV_getResourceForNode(aNode)
{
var uri = aNode.uri;
NS_ASSERT(uri, "if there is no uri, we can't persist the open state");
@ -916,7 +911,7 @@ PlacesTreeView.prototype = {
},
getCellProperties: function PTV_getCellProperties(aRow, aColumn, aProperties) {
var columnType = aColumn.id || aColumn.element.getAttribute("anonid") ;
var columnType = aColumn.id || aColumn.element.getAttribute("anonid");
if (columnType != "title")
return;
@ -933,16 +928,14 @@ PlacesTreeView.prototype = {
this._ensureValidRow(aRow);
var node = this._visibleElements[aRow];
if (PlacesUtils.nodeIsContainer(node)) {
// the root node is always expandable
if (!node.parent)
return true;
// treat non-expandable queries as non-containers
if (PlacesUtils.nodeIsQuery(node)) {
asQuery(node);
if (node.queryOptions.expandQueries)
return true;
// the root node is always expandable
if (!node.parent)
return true;
return false;
return node.queryOptions.expandQueries;
}
return true;
}
@ -954,7 +947,7 @@ PlacesTreeView.prototype = {
if (!PlacesUtils.nodeIsContainer(this._visibleElements[aRow]))
throw Cr.NS_ERROR_INVALID_ARG;
return asContainer(this._visibleElements[aRow]).containerOpen;
return this._visibleElements[aRow].containerOpen;
},
isContainerEmpty: function PTV_isContainerEmpty(aRow) {
@ -962,7 +955,7 @@ PlacesTreeView.prototype = {
if (!PlacesUtils.nodeIsContainer(this._visibleElements[aRow]))
throw Cr.NS_ERROR_INVALID_ARG;
return !asContainer(this._visibleElements[aRow]).hasChildren;
return !this._visibleElements[aRow].hasChildren;
},
isSeparator: function PTV_isSeparator(aRow) {
@ -1003,8 +996,15 @@ PlacesTreeView.prototype = {
return false;
}
return this._visibleElements[aRow].indentLevel ==
this._visibleElements[aRow + 1].indentLevel;
var thisLevel = this._visibleElements[aRow].indentLevel;
for (var i = aAfterIndex + 1; i < this._visibleElements.length; ++i) {
var nextLevel = this._visibleElements[i].indentLevel;
if (nextLevel == thisLevel)
return true;
if (nextLevel < thisLevel)
break;
}
return false;
},
getLevel: function PTV_getLevel(aRow) {
@ -1133,7 +1133,6 @@ PlacesTreeView.prototype = {
if (!PlacesUtils.nodeIsContainer(node))
return; // not a container, nothing to do
asContainer(node);
var resource = this._getResourceForNode(node);
if (resource) {
const openLiteral = PlacesUtils.RDF.GetResource("http://home.netscape.com/NC-rdf#open");
@ -1304,5 +1303,4 @@ function PlacesTreeView(aShowRoot) {
this._visibleElements = [];
this._observers = [];
this._showRoot = aShowRoot;
this._ignoreInvalidateContainer = false;
}

Просмотреть файл

@ -95,119 +95,92 @@ var PlacesUtils = {
/**
* The Bookmarks Service.
*/
_bookmarks: null,
get bookmarks() {
if (!this._bookmarks) {
this._bookmarks = Cc["@mozilla.org/browser/nav-bookmarks-service;1"].
getService(Ci.nsINavBookmarksService);
}
return this._bookmarks;
delete this.bookmarks;
return this.bookmarks = Cc["@mozilla.org/browser/nav-bookmarks-service;1"].
getService(Ci.nsINavBookmarksService);
},
/**
* The Nav History Service.
*/
_history: null,
get history() {
if (!this._history) {
this._history = Cc["@mozilla.org/browser/nav-history-service;1"].
getService(Ci.nsINavHistoryService);
}
return this._history;
delete this.history;
return this.history = Cc["@mozilla.org/browser/nav-history-service;1"].
getService(Ci.nsINavHistoryService);
},
/**
* The Live Bookmark Service.
*/
_livemarks: null,
get livemarks() {
if (!this._livemarks) {
this._livemarks = Cc["@mozilla.org/browser/livemark-service;2"].
getService(Ci.nsILivemarkService);
}
return this._livemarks;
delete this.livemarks;
return this.livemarks = Cc["@mozilla.org/browser/livemark-service;2"].
getService(Ci.nsILivemarkService);
},
/**
* The Annotations Service.
*/
_annotations: null,
get annotations() {
if (!this._annotations) {
this._annotations = Cc["@mozilla.org/browser/annotation-service;1"].
getService(Ci.nsIAnnotationService);
}
return this._annotations;
delete this.annotations;
return this.annotations = Cc["@mozilla.org/browser/annotation-service;1"].
getService(Ci.nsIAnnotationService);
},
/**
* The Favicons Service
*/
_favicons: null,
get favicons() {
if (!this._favicons) {
this._favicons = Cc["@mozilla.org/browser/favicon-service;1"].
getService(Ci.nsIFaviconService);
}
return this._favicons;
delete this.favicons;
return this.favicons = Cc["@mozilla.org/browser/favicon-service;1"].
getService(Ci.nsIFaviconService);
},
/**
* The Microsummary Service
*/
_microsummaries: null,
get microsummaries() {
if (!this._microsummaries)
this._microsummaries = Cc["@mozilla.org/microsummary/service;1"].
getService(Ci.nsIMicrosummaryService);
return this._microsummaries;
delete this.microsummaries;
return this.microsummaries = Cc["@mozilla.org/microsummary/service;1"].
getService(Ci.nsIMicrosummaryService);
},
/**
* The Places Tagging Service
*/
get tagging() {
if (!this._tagging)
this._tagging = Cc["@mozilla.org/browser/tagging-service;1"].
getService(Ci.nsITaggingService);
return this._tagging;
delete this.tagging;
return this.tagging = Cc["@mozilla.org/browser/tagging-service;1"].
getService(Ci.nsITaggingService);
},
_RDF: null,
get RDF() {
if (!this._RDF)
this._RDF = Cc["@mozilla.org/rdf/rdf-service;1"].
getService(Ci.nsIRDFService);
return this._RDF;
delete this.RDF;
return this.RDF = Cc["@mozilla.org/rdf/rdf-service;1"].
getService(Ci.nsIRDFService);
},
_localStore: null,
get localStore() {
if (!this._localStore)
this._localStore = this.RDF.GetDataSource("rdf:local-store");
return this._localStore;
delete this.localStore;
return this.localStore = this.RDF.GetDataSource("rdf:local-store");
},
get tm() {
return this.ptm.transactionManager;
delete this.tm;
return this.tm = this.ptm.transactionManager;
},
_ptm: null,
get ptm() {
if (!this._ptm) {
this._ptm = Cc["@mozilla.org/browser/placesTransactionsService;1"].
getService(Components.interfaces.nsIPlacesTransactionsService);
}
return this._ptm;
delete this.ptm;
return this.ptm = Cc["@mozilla.org/browser/placesTransactionsService;1"].
getService(Ci.nsIPlacesTransactionsService);
},
_clipboard: null,
get clipboard() {
if (!this._clipboard) {
this._clipboard = Cc["@mozilla.org/widget/clipboard;1"].
getService(Ci.nsIClipboard);
}
return this._clipboard;
delete this.clipboard;
return this.clipboard = Cc["@mozilla.org/widget/clipboard;1"].
getService(Ci.nsIClipboard);
},
/**
@ -218,9 +191,7 @@ var PlacesUtils = {
*/
_uri: function PU__uri(aSpec) {
NS_ASSERT(aSpec, "empty URL spec");
var ios = Cc["@mozilla.org/network/io-service;1"].
getService(Ci.nsIIOService);
return ios.newURI(aSpec, null, null);
return IO.newURI(aSpec);
},
/**
@ -239,16 +210,13 @@ var PlacesUtils = {
/**
* String bundle helpers
*/
__bundle: null,
get _bundle() {
if (!this.__bundle) {
const PLACES_STRING_BUNDLE_URI =
const PLACES_STRING_BUNDLE_URI =
"chrome://browser/locale/places/places.properties";
this.__bundle = Cc["@mozilla.org/intl/stringbundle;1"].
getService(Ci.nsIStringBundleService).
createBundle(PLACES_STRING_BUNDLE_URI);
}
return this.__bundle;
delete this._bundle;
return this._bundle = Cc["@mozilla.org/intl/stringbundle;1"].
getService(Ci.nsIStringBundleService).
createBundle(PLACES_STRING_BUNDLE_URI);
},
getFormattedString: function PU_getFormattedString(key, params) {
@ -315,14 +283,12 @@ var PlacesUtils = {
* A result node
* @returns true if the node is a URL item, false otherwise
*/
uriTypes: [Ci.nsINavHistoryResultNode.RESULT_TYPE_URI,
Ci.nsINavHistoryResultNode.RESULT_TYPE_VISIT,
Ci.nsINavHistoryResultNode.RESULT_TYPE_FULL_VISIT],
nodeIsURI: function PU_nodeIsURI(aNode) {
NS_ASSERT(aNode, "null node");
const NHRN = Ci.nsINavHistoryResultNode;
var type = aNode.type;
return type == NHRN.RESULT_TYPE_URI ||
type == NHRN.RESULT_TYPE_VISIT ||
type == NHRN.RESULT_TYPE_FULL_VISIT;
return this.uriTypes.indexOf(aNode.type) != -1;
},
/**
@ -333,7 +299,6 @@ var PlacesUtils = {
*/
nodeIsQuery: function PU_nodeIsQuery(aNode) {
NS_ASSERT(aNode, "null node");
return aNode.type == Ci.nsINavHistoryResultNode.RESULT_TYPE_QUERY;
},
@ -362,7 +327,6 @@ var PlacesUtils = {
*/
nodeIsHost: function PU_nodeIsHost(aNode) {
NS_ASSERT(aNode, "null node");
return aNode.type == Ci.nsINavHistoryResultNode.RESULT_TYPE_HOST;
},
@ -372,16 +336,14 @@ var PlacesUtils = {
* A result node
* @returns true if the node is a container item, false otherwise
*/
containerTypes: [Ci.nsINavHistoryResultNode.RESULT_TYPE_FOLDER,
Ci.nsINavHistoryResultNode.RESULT_TYPE_QUERY,
Ci.nsINavHistoryResultNode.RESULT_TYPE_HOST,
Ci.nsINavHistoryResultNode.RESULT_TYPE_DAY,
Ci.nsINavHistoryResultNode.RESULT_TYPE_DYNAMIC_CONTAINER],
nodeIsContainer: function PU_nodeIsContainer(aNode) {
NS_ASSERT(aNode, "null node");
const NHRN = Ci.nsINavHistoryResultNode;
var type = aNode.type;
return type == NHRN.RESULT_TYPE_HOST ||
type == NHRN.RESULT_TYPE_QUERY ||
type == NHRN.RESULT_TYPE_FOLDER ||
type == NHRN.RESULT_TYPE_DAY ||
type == NHRN.RESULT_TYPE_DYNAMIC_CONTAINER;
return this.containerTypes.indexOf(aNode.type) != -1;
},
/**
@ -448,14 +410,22 @@ var PlacesUtils = {
NS_ASSERT(aNode, "null node");
var parent = aNode.parent;
if (!parent || !PlacesUtils.nodeIsContainer(parent))
if (!parent)
return -1;
var wasOpen = parent.containerOpen;
parent.containerOpen = true;
var result, oldViewer;
if (!wasOpen) {
result = parent.parentResult;
oldViewer = result.viewer;
result.viewer = null;
parent.containerOpen = true;
}
var cc = parent.childCount;
asContainer(parent);
for (var i = 0; i < cc && parent.getChild(i) != aNode; ++i);
parent.containerOpen = wasOpen;
if (!wasOpen) {
parent.containerOpen = false;
result.viewer = oldViewer;
}
return i < cc ? i : -1;
},
@ -650,7 +620,7 @@ var PlacesUtils = {
* @returns A nsITransaction object that performs the copy.
*/
_getURIItemCopyTransaction: function (aData, aContainer, aIndex) {
return this.ptm.createItem(this._uri(aData.uri), aContainer, aIndex,
return this.ptm.createItem(IO.newURI(aData.uri), aContainer, aIndex,
aData.title, "");
},
@ -671,7 +641,7 @@ var PlacesUtils = {
_getBookmarkItemCopyTransaction:
function PU__getBookmarkItemCopyTransaction(aData, aContainer, aIndex,
aExcludeAnnotations) {
var itemURL = this._uri(aData.uri);
var itemURL = IO.newURI(aData.uri);
var itemTitle = aData.title;
var keyword = aData.keyword;
var annos = aData.annos;
@ -724,8 +694,8 @@ var PlacesUtils = {
folderItemsTransactions);
}
else { // node is a livemark
var feedURI = self._uri(node.uri.feed);
var siteURI = self._uri(node.uri.site);
var feedURI = IO.newURI(node.uri.feed);
var siteURI = IO.newURI(node.uri.site);
txn = self.ptm.createLivemark(feedURI, siteURI, node.title,
aContainer, index, node.annos);
}
@ -776,8 +746,8 @@ var PlacesUtils = {
for (var i = 0; i < parts.length; i=i+2) {
var uriString = parts[i];
var titleString = parts[i+1];
// note: this._uri() will throw if uriString is not a valid URI
if (this._uri(uriString)) {
// note: IO.newURI() will throw if uriString is not a valid URI
if (IO.newURI(uriString)) {
nodes.push({ uri: uriString,
title: titleString ? titleString : uriString });
}
@ -787,8 +757,8 @@ var PlacesUtils = {
var parts = blob.split("\n");
for (var i = 0; i < parts.length; i++) {
var uriString = parts[i];
// note: this._uri() will throw if uriString is not a valid URI
if (uriString != "" && this._uri(uriString))
// note: IO.newURI() will throw if uriString is not a valid URI
if (uriString != "" && IO.newURI(uriString))
nodes.push({ uri: uriString, title: uriString });
}
break;
@ -826,8 +796,8 @@ var PlacesUtils = {
}
else if (copy) {
// Place is a Livemark Container, should be reinstantiated
var feedURI = this._uri(data.uri.feed);
var siteURI = this._uri(data.uri.site);
var feedURI = IO.newURI(data.uri.feed);
var siteURI = IO.newURI(data.uri.site);
return this.ptm.createLivemark(feedURI, siteURI, data.title, container,
index, data.annos);
}
@ -855,7 +825,7 @@ var PlacesUtils = {
default:
if (type == this.TYPE_X_MOZ_URL || type == this.TYPE_UNICODE) {
var title = (type == this.TYPE_X_MOZ_URL) ? data.title : data.uri;
return this.ptm.createItem(this._uri(data.uri), container, index,
return this.ptm.createItem(IO.newURI(data.uri), container, index,
title);
}
return null;
@ -892,7 +862,6 @@ var PlacesUtils = {
var result = this.history.executeQuery(query, options);
result.root.containerOpen = true;
asContainer(result.root);
return result;
},
@ -1270,7 +1239,7 @@ var PlacesUtils = {
*/
checkURLSecurity: function PU_checkURLSecurity(aURINode) {
if (!this.nodeIsBookmark(aURINode)) {
var uri = this._uri(aURINode.uri);
var uri = IO.newURI(aURINode.uri);
if (uri.schemeIs("javascript") || uri.schemeIs("data")) {
const BRANDING_BUNDLE_URI = "chrome://branding/locale/brand.properties";
var brandShortName = Cc["@mozilla.org/intl/stringbundle;1"].
@ -1557,15 +1526,27 @@ var PlacesUtils = {
}
}
else {
let wasOpen = aNode.containerOpen;
if (!wasOpen)
aNode.containerOpen = true;
for (let i = 0; i < aNode.childCount; ++i) {
let child = aNode.getChild(i);
if (this.nodeIsURI(child))
urls.push(child.uri);
let result, oldViewer;
try {
let wasOpen = aNode.containerOpen;
if (!wasOpen) {
result = aNode.parentResult;
oldViewer = result.viewer;
result.viewer = null;
aNode.containerOpen = true;
}
for (let i = 0; i < aNode.childCount; ++i) {
let child = aNode.getChild(i);
if (this.nodeIsURI(child))
urls.push(child.uri);
}
if (!wasOpen)
aNode.containerOpen = false;
}
finally {
if (oldViewer)
result.viewer = oldViewer;
}
aNode.containerOpen = wasOpen;
}
return urls;
@ -1646,22 +1627,70 @@ var PlacesUtils = {
this._openTabset(urlsToOpen, aEvent);
},
_placesFlavors: null,
get placesFlavors() {
if (!this._placesFlavors) {
var placeTypes = [PlacesUtils.TYPE_X_MOZ_PLACE_CONTAINER,
PlacesUtils.TYPE_X_MOZ_PLACE_SEPARATOR,
PlacesUtils.TYPE_X_MOZ_PLACE];
this._placesFlavors = Cc["@mozilla.org/supports-array;1"].
createInstance(Ci.nsISupportsArray);
for (var i = 0; i < placeTypes.length; ++i) {
var cstring = Cc["@mozilla.org/supports-cstring;1"].
createInstance(Ci.nsISupportsCString);
cstring.data = placeTypes[i];
this._placesFlavors.AppendElement(cstring);
}
delete this.placesFlavors;
var placeTypes = [PlacesUtils.TYPE_X_MOZ_PLACE_CONTAINER,
PlacesUtils.TYPE_X_MOZ_PLACE_SEPARATOR,
PlacesUtils.TYPE_X_MOZ_PLACE];
this.placesFlavors = Cc["@mozilla.org/supports-array;1"].
createInstance(Ci.nsISupportsArray);
for (var i = 0; i < placeTypes.length; ++i) {
var cstring = Cc["@mozilla.org/supports-cstring;1"].
createInstance(Ci.nsISupportsCString);
cstring.data = placeTypes[i];
this.placesFlavors.AppendElement(cstring);
}
return this._placesFlavors;
return this.placesFlavors;
},
/**
* Helper for the toolbar and menu views
*/
createMenuItemForNode: function(aNode, aContainersMap) {
var element;
var type = aNode.type;
if (type == Ci.nsINavHistoryResultNode.RESULT_TYPE_SEPARATOR)
element = document.createElement("menuseparator");
else {
var iconURI = aNode.icon;
var iconURISpec = "";
if (iconURI)
iconURISpec = iconURI.spec;
if (this.uriTypes.indexOf(type) != -1) {
element = document.createElement("menuitem");
element.setAttribute("statustext", aNode.uri);
element.className = "menuitem-iconic bookmark-item";
}
else if (this.containerTypes.indexOf(type) != -1) {
element = document.createElement("menu");
element.setAttribute("container", "true");
if (iconURISpec == "chrome://browser/skin/places/livemarkItem.png")
element.setAttribute("livemark", "true");
var popup = document.createElement("menupopup");
popup._resultNode = asContainer(aNode);
#ifndef XP_MACOSX
// no context menu on mac
popup.setAttribute("context", "placesContext");
#endif
element.appendChild(popup);
if (aContainersMap)
aContainersMap.push({ resultNode: aNode, domNode: popup });
element.className = "menu-iconic bookmark-item";
}
else
throw "Unexpected node";
element.setAttribute("label", aNode.title);
if (iconURISpec)
element.setAttribute("image", iconURISpec);
}
element.node = aNode;
element.node.viewIndex = 0;
return element;
}
};

Просмотреть файл

@ -121,11 +121,13 @@ static NS_DEFINE_CID(kParserCID, NS_PARSER_CID);
#define KEY_MICSUM_GEN_URI_LOWER "micsum_gen_uri"
#define KEY_DATE_ADDED_LOWER "add_date"
#define KEY_LAST_MODIFIED_LOWER "last_modified"
#define KEY_GENERATED_TITLE_LOWER "generated_title"
#define LOAD_IN_SIDEBAR_ANNO NS_LITERAL_CSTRING("bookmarkProperties/loadInSidebar")
#define DESCRIPTION_ANNO NS_LITERAL_CSTRING("bookmarkProperties/description")
#define POST_DATA_ANNO NS_LITERAL_CSTRING("URIProperties/POSTData")
#define LAST_CHARSET_ANNO NS_LITERAL_CSTRING("URIProperties/characterSet")
#define STATIC_TITLE_ANNO NS_LITERAL_CSTRING("bookmarks/staticTitle")
#define BOOKMARKS_MENU_ICON_URI "chrome://browser/skin/places/bookmarksMenu.png"
@ -208,6 +210,13 @@ public:
// and the livemark title is known, we can create it.
nsCOMPtr<nsIURI> mPreviousFeed;
// contains the text content of the previous microsummary, so that when the
// link ends, we can replace the bookmark's title with it and store the user's
// title in the staticTitle annotation.
nsString mPreviousMicrosummaryText;
nsCOMPtr<nsIMicrosummary> mPreviousMicrosummary;
void ConsumeHeading(nsAString* aHeading, ContainerType* aContainerType)
{
*aHeading = mPreviousText;
@ -791,6 +800,10 @@ BookmarkContentSink::HandleLinkBegin(const nsIParserNode& node)
// mPreviousText will hold our link text, clear it so that can be appended to
frame.mPreviousText.Truncate();
// Empty our microsummary items from the previous frame.
frame.mPreviousMicrosummary = nsnull;
frame.mPreviousMicrosummaryText.Truncate();
// get the attributes we care about
nsAutoString href;
@ -803,6 +816,7 @@ BookmarkContentSink::HandleLinkBegin(const nsIParserNode& node)
nsAutoString webPanel;
nsAutoString itemId;
nsAutoString micsumGenURI;
nsAutoString generatedTitle;
nsAutoString dateAdded;
nsAutoString lastModified;
@ -827,6 +841,8 @@ BookmarkContentSink::HandleLinkBegin(const nsIParserNode& node)
webPanel = node.GetValueAt(i);
} else if (key.LowerCaseEqualsLiteral(KEY_MICSUM_GEN_URI_LOWER)) {
micsumGenURI = node.GetValueAt(i);
} else if (key.LowerCaseEqualsLiteral(KEY_GENERATED_TITLE_LOWER)) {
generatedTitle = node.GetValueAt(i);
} else if (key.LowerCaseEqualsLiteral(KEY_DATE_ADDED_LOWER)) {
dateAdded = node.GetValueAt(i);
} else if (key.LowerCaseEqualsLiteral(KEY_LAST_MODIFIED_LOWER)) {
@ -843,6 +859,7 @@ BookmarkContentSink::HandleLinkBegin(const nsIParserNode& node)
webPanel.Trim(kWhitespace);
itemId.Trim(kWhitespace);
micsumGenURI.Trim(kWhitespace);
generatedTitle.Trim(kWhitespace);
dateAdded.Trim(kWhitespace);
lastModified.Trim(kWhitespace);
@ -946,15 +963,12 @@ BookmarkContentSink::HandleLinkBegin(const nsIParserNode& node)
}
// import microsummary
// Note: expiration and generated title are ignored, and will be recalculated
// by the microsummary service
if (!micsumGenURI.IsEmpty()) {
nsCOMPtr<nsIURI> micsumGenURIObject;
if (NS_SUCCEEDED(NS_NewURI(getter_AddRefs(micsumGenURIObject), micsumGenURI))) {
nsCOMPtr<nsIMicrosummary> microsummary;
mMicrosummaryService->CreateMicrosummary(frame.mPreviousLink, micsumGenURIObject,
getter_AddRefs(microsummary));
mMicrosummaryService->SetMicrosummary(frame.mPreviousId, microsummary);
getter_AddRefs(frame.mPreviousMicrosummary));
frame.mPreviousMicrosummaryText = generatedTitle;
}
}
@ -1048,7 +1062,17 @@ BookmarkContentSink::HandleLinkEnd()
printf("Creating bookmark '%s' %lld\n",
NS_ConvertUTF16toUTF8(frame.mPreviousText).get(), frame.mPreviousId);
#endif
mBookmarksService->SetItemTitle(frame.mPreviousId, frame.mPreviousText);
if (frame.mPreviousMicrosummary) {
rv = mAnnotationService->SetItemAnnotationString(frame.mPreviousId, STATIC_TITLE_ANNO,
frame.mPreviousText, 0,
nsIAnnotationService::EXPIRE_NEVER);
NS_ASSERTION(NS_SUCCEEDED(rv), "Could not store user's bookmark title!");
mBookmarksService->SetItemTitle(frame.mPreviousId, frame.mPreviousMicrosummaryText);
mMicrosummaryService->SetMicrosummary(frame.mPreviousId, frame.mPreviousMicrosummary);
}
else
mBookmarksService->SetItemTitle(frame.mPreviousId, frame.mPreviousText);
}
// Set last-modified-date for bookmarks and livemarks here so that the

Просмотреть файл

@ -718,6 +718,14 @@ var feedHandlerInfo = {
this.element(PREF_FEED_SELECTED_ACTION).value = "reader";
},
// Whether or not we are currently storing the action selected by the user.
// We use this to suppress notification-triggered updates to the list when
// we make changes that may spawn such updates, specifically when we change
// the action for the feed type, which results in feed preference updates,
// which spawn "pref changed" notifications that would otherwise cause us
// to rebuild the view unnecessarily.
_storingAction: false,
//**************************************************************************//
// nsIMIMEInfo
@ -881,7 +889,7 @@ var gApplicationsPane = {
observe: function (aSubject, aTopic, aData) {
// Rebuild the list when there are changes to preferences that influence
// whether or not to show certain entries in the list.
if (aTopic == "nsPref:changed") {
if (aTopic == "nsPref:changed" && !this._storingAction) {
// These two prefs alter the list of visible types, so we have to rebuild
// that list when they change.
if (aData == PREF_SHOW_PLUGINS_IN_LIST ||
@ -1450,6 +1458,17 @@ var gApplicationsPane = {
// Changes
onSelectAction: function(aActionItem) {
this._storingAction = true;
try {
this._storeAction(aActionItem);
}
finally {
this._storingAction = false;
}
},
_storeAction: function(aActionItem) {
var typeItem = this._list.selectedItem;
var handlerInfo = this._handledTypes[typeItem.type];
@ -1499,13 +1518,43 @@ var gApplicationsPane = {
// as we handle it specially ourselves.
aEvent.stopPropagation();
var handlerApp;
#ifdef XP_WIN
var params = {};
var handlerInfo = this._handledTypes[this._list.selectedItem.type];
if (handlerInfo.type == TYPE_MAYBE_FEED) {
// MIME info will be null, create a temp object.
params.mimeInfo = this._mimeSvc.getFromTypeAndExtension(handlerInfo.type,
handlerInfo.primaryExtension);
} else {
params.mimeInfo = handlerInfo.wrappedHandlerInfo;
}
params.title = this._prefsBundle.getString("fpTitleChooseApp");
params.description = handlerInfo.description;
params.filename = null;
params.handlerApp = null;
window.openDialog("chrome://global/content/appPicker.xul", null,
"chrome,modal,centerscreen,titlebar,dialog=yes",
params);
if (params.handlerApp &&
params.handlerApp.executable &&
params.handlerApp.executable.isFile()) {
handlerApp = params.handlerApp;
// Add the app to the type's list of possible handlers.
handlerInfo.possibleApplicationHandlers.appendElement(handlerApp, false);
}
#else
var fp = Cc["@mozilla.org/filepicker;1"].createInstance(Ci.nsIFilePicker);
var winTitle = this._prefsBundle.getString("fpTitleChooseApp");
fp.init(window, winTitle, Ci.nsIFilePicker.modeOpen);
fp.appendFilters(Ci.nsIFilePicker.filterApps);
var handlerApp;
// Prompt the user to pick an app. If they pick one, and it's a valid
// selection, then add it to the list of possible handlers.
if (fp.show() == Ci.nsIFilePicker.returnOK && fp.file &&
@ -1519,6 +1568,7 @@ var gApplicationsPane = {
let handlerInfo = this._handledTypes[this._list.selectedItem.type];
handlerInfo.possibleApplicationHandlers.appendElement(handlerApp, false);
}
#endif
// Rebuild the actions menu whether the user picked an app or canceled.
// If they picked an app, we want to add the app to the menu and select it.

Просмотреть файл

@ -85,7 +85,7 @@
style="&prefWin.styleWin;">
#else
#ifdef XP_MACOSX
style="&prefWindow.styleMac;">
style="&prefWin.styleMac;">
#else
style="&prefWin.styleGNOME;">
#endif

Просмотреть файл

@ -234,9 +234,9 @@ var gSecurityPane = {
var popup = document.getElementById(onloadPopupId);
if (!popup) {
var providerBranch = Cc["@mozilla.org/preferences-service;1"]
.getService(Ci.nsIPrefService)
.getBranch("browser.safebrowsing.provider.");
var providerBranch = Cc["@mozilla.org/preferences-service;1"].
getService(Ci.nsIPrefService).
getBranch("browser.safebrowsing.provider.");
// fill in onload phishing list data -- but require a privacy policy
// URL be provided, and require it to be at a chrome URL so it's always
@ -374,8 +374,8 @@ var gSecurityPane = {
_masterPasswordSet: function ()
{
const Cc = Components.classes, Ci = Components.interfaces;
var secmodDB = Cc["@mozilla.org/security/pkcs11moduledb;1"]
.getService(Ci.nsIPKCS11ModuleDB);
var secmodDB = Cc["@mozilla.org/security/pkcs11moduledb;1"].
getService(Ci.nsIPKCS11ModuleDB);
var slot = secmodDB.findSlotByName("");
if (slot) {
var status = slot.status;
@ -419,9 +419,12 @@ var gSecurityPane = {
*/
_removeMasterPassword: function ()
{
var secmodDB = Components.classes["@mozilla.org/security/pkcs11moduledb;1"]
.getService(Components.interfaces.nsIPKCS11ModuleDB);
const Cc = Components.classes, Ci = Components.interfaces;
var secmodDB = Cc["@mozilla.org/security/pkcs11moduledb;1"].
getService(Ci.nsIPKCS11ModuleDB);
if (secmodDB.isFIPSEnabled) {
var promptService = Cc["@mozilla.org/embedcomp/prompt-service;1"].
getService(Ci.nsIPromptService);
var bundle = document.getElementById("bundlePreferences");
promptService.alert(window,
bundle.getString("pw_change_failed_title"),

Просмотреть файл

@ -38,8 +38,8 @@
var gDataProvider = null;
// An instance of our application is a PROT_Application object. It
// basically just populates a few globals and instantiates wardens and
// the listmanager.
// basically just populates a few globals and instantiates wardens,
// the listmanager, and the about:blocked error page.
/**
* An instance of our application. There should be exactly one of these.
@ -100,3 +100,30 @@ function PROT_Application() {
PROT_Application.prototype.getReportURL = function(name) {
return gDataProvider["getReport" + name + "URL"]();
}
/**
* about:blocked implementation
*/
PROT_Application.prototype.newChannel = function(uri) {
var ioService = Cc["@mozilla.org/network/io-service;1"]
.getService(Ci.nsIIOService);
var childURI = ioService.newURI("chrome://browser/content/safebrowsing/blockedSite.xhtml",
null, null);
var channel = ioService.newChannelFromURI(childURI);
channel.originalURI = uri;
return channel;
}
PROT_Application.prototype.getURIFlags = function(uri) {
return Ci.nsIAboutModule.ALLOW_SCRIPT;
}
PROT_Application.prototype.QueryInterface = function(iid) {
if (iid.equals(Ci.nsISupports) ||
iid.equals(Ci.nsIAboutModule))
return this;
Components.returnCode = Components.results.NS_ERROR_NO_INTERFACE;
return null;
}

Просмотреть файл

@ -0,0 +1,210 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html [
<!ENTITY % htmlDTD PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "DTD/xhtml1-strict.dtd">
%htmlDTD;
<!ENTITY % globalDTD SYSTEM "chrome://global/locale/global.dtd">
%globalDTD;
<!ENTITY % brandDTD SYSTEM "chrome://branding/locale/brand.dtd" >
%brandDTD;
<!ENTITY % blockedSiteDTD SYSTEM "chrome://browser/locale/safebrowsing/phishing-afterload-warning-message.dtd">
%blockedSiteDTD;
]>
<!-- ***** BEGIN LICENSE BLOCK *****
- Version: MPL 1.1/GPL 2.0/LGPL 2.1
-
- The contents of this file are subject to the Mozilla Public License Version
- 1.1 (the "License"); you may not use this file except in compliance with
- the License. You may obtain a copy of the License at
- http://www.mozilla.org/MPL/
-
- Software distributed under the License is distributed on an "AS IS" basis,
- WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
- for the specific language governing rights and limitations under the
- License.
-
- The Original Code is mozilla.org code.
-
- The Initial Developer of the Original Code is
- Netscape Communications Corporation.
- Portions created by the Initial Developer are Copyright (C) 1998
- the Initial Developer. All Rights Reserved.
-
- Contributor(s):
- Adam Lock <adamlock@netscape.com>
- William R. Price <wrprice@alumni.rice.edu>
- Henrik Skupin <mozilla@hskupin.info>
- Jeff Walden <jwalden+code@mit.edu>
- Johnathan Nightingale <johnath@mozilla.com>
-
- Alternatively, the contents of this file may be used under the terms of
- either the GNU General Public License Version 2 or later (the "GPL"), or
- the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
- in which case the provisions of the GPL or the LGPL are applicable instead
- of those above. If you wish to allow use of your version of this file only
- under the terms of either the GPL or the LGPL, and not to allow others to
- use your version of this file under the terms of the MPL, indicate your
- decision by deleting the provisions above and replace them with the notice
- and other provisions required by the LGPL or the GPL. If you do not delete
- the provisions above, a recipient may use your version of this file under
- the terms of any one of the MPL, the GPL or the LGPL.
-
- ***** END LICENSE BLOCK ***** -->
<html xmlns="http://www.w3.org/1999/xhtml" class="blacklist">
<head>
<link rel="stylesheet" href="chrome://global/skin/netError.css" type="text/css" media="all" />
<link rel="icon" type="image/png" id="favicon" href="chrome://global/skin/icons/blacklist_favicon.png"/>
<script type="application/javascript" src="chrome://global/content/strres.js"/>
<script type="application/javascript"><![CDATA[
// Error url MUST be formatted like this:
// about:blocked?e=error_code&u=url
// Note that this file uses document.documentURI to get
// the URL (with the format from above). This is because
// document.location.href gets the current URI off the docshell,
// which is the URL displayed in the location bar, i.e.
// the URI that the user attempted to load.
function getErrorCode()
{
var url = document.documentURI;
var error = url.search(/e\=/);
var duffUrl = url.search(/\&u\=/);
return decodeURIComponent(url.slice(error + 2, duffUrl));
}
function getURL()
{
var url = document.documentURI;
var index = url.search(/u\=/);
// index == -1 if not found; if so, return an empty string
// instead of what would turn out to be portions of the URI
if (index == -1)
return "";
return decodeURIComponent(url.slice(index + 2));
}
/**
* Attempt to parse the result of getURL and extract a hostname. Fail back
* to getURL so that we always return something meaningful.
*/
function getHostString()
{
var ios = Components.classes["@mozilla.org/network/io-service;1"]
.getService(Components.interfaces.nsIIOService);
var url = getURL();
try {
return ios.newURI(url, null, null).host;
} catch (e) {
return url;
}
}
// Elements that tend to need content set
var errorTitleText, errorShortDescText, errorLongDesc, errorLongDescText;
// The string bundles managing strings for various blocked page scenarios
var sb = srGetStrBundle("chrome://browser/locale/safebrowsing/blockedSite.properties");
var brandBundle = srGetStrBundle("chrome://branding/locale/brand.properties");
var brandShortName = brandBundle.GetStringFromName("brandShortName");
function initPage()
{
// Set up the cached elements
errorTitleText = document.getElementById("errorTitleText");
errorShortDescText = document.getElementById("errorShortDescText");
errorLongDesc = document.getElementById("errorLongDesc");
errorLongDescText = document.getElementById("errorLongDescText");
// Handoff to the appropriate initializer, based on error code
switch(getErrorCode()) {
case "malwareBlocked" :
initPage_malware();
break;
case "phishingBlocked" :
initPage_phishing();
break;
}
}
/**
* Initialize custom strings and functionality for blocked malware case
*/
function initPage_malware()
{
document.title = sb.GetStringFromName("malware.title");
errorTitleText.textContent = document.title;
errorShortDescText.textContent = sb.formatStringFromName("malware.shortDesc",
[getHostString()], 1);
errorLongDesc.innerHTML = sb.GetStringFromName("malware.longDesc");
}
/**
* Initialize custom strings and functionality for blocked phishing case
*/
function initPage_phishing()
{
document.title = sb.GetStringFromName("phishing.title");
errorTitleText.textContent = document.title;
errorShortDescText.textContent = sb.formatStringFromName("phishing.shortDesc",
[getHostString()], 1);
var longDesc = sb.GetStringFromName("phishing.longDesc");
// If we have a more-info link for the phishing information, add it in,
// otherwise just use the generic text
var faqURL = Components.classes["@mozilla.org/toolkit/URLFormatterService;1"]
.getService(Components.interfaces.nsIURLFormatter)
.formatURLPref("browser.safebrowsing.warning.infoURL");
if(faqURL && faqURL != "about:blank") {
longDesc += sb.formatStringFromName("phishing.learnMoreLink",
[brandShortName], 1);
errorLongDesc.innerHTML = longDesc;
document.getElementById("faqLink").setAttribute("href", faqURL);
}
else
errorLongDesc.innerHTML = longDesc;
}
]]></script>
</head>
<body dir="&locale.dir;">
<div id="errorPageContainer">
<!-- Error Title -->
<div id="errorTitle">
<h1 id="errorTitleText" />
</div>
<div id="errorLongContent">
<!-- Short Description -->
<div id="errorShortDesc">
<p id="errorShortDescText" />
</div>
<!-- Long Description -->
<div id="errorLongDesc">
<p id="errorLongDescText" />
</div>
<!-- Action buttons -->
<div id="buttons">
<xul:button xmlns:xul="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul"
id="getMeOutButton" label="&safeb.palm.accept.label;" oncommand="window.home();" />
</div>
</div>
</div>
<!--
- Note: It is important to run the script this way, instead of using
- an onload handler. This is because error pages are loaded as
- LOAD_BACKGROUND, which means that onload handlers will not be executed.
-->
<script type="application/javascript">initPage();</script>
</body>
</html>

Просмотреть файл

@ -64,6 +64,13 @@ function PROT_MalwareWarden() {
"a:1:" + testData.length + "\n" +
testData +
"\n";
testData = "mozilla.com/firefox/its-a-trap.html";
testUpdate +=
"n:1000\ni:test-phish-simple\nad:1\n" +
"a:1:" + testData.length + "\n" +
testData +
"\n";
var dbService_ = Cc["@mozilla.org/url-classifier/dbservice;1"]
.getService(Ci.nsIUrlClassifierDBService);

Просмотреть файл

@ -208,7 +208,6 @@ PROT_PhishMsgDisplayerBase.prototype.browserSelected = function() {
this.messageShouldShow_ = true;
}
this.hideLockIcon_(); // Comes back when we are unselected or unloaded
this.addWarningInUrlbar_(); // Goes away when we are unselected or unloaded
// messageShouldShow might be false if the user dismissed the warning,
@ -234,7 +233,6 @@ PROT_PhishMsgDisplayerBase.prototype.explicitShow = function() {
*/
PROT_PhishMsgDisplayerBase.prototype.browserUnselected = function() {
this.removeWarningInUrlbar_();
this.unhideLockIcon_();
if (this.messageShowing_)
this.hideMessage_();
}
@ -290,7 +288,6 @@ PROT_PhishMsgDisplayerBase.prototype.done = function() {
// If we were started, we must be the current problem, so these things
// must be showing
this.removeWarningInUrlbar_();
this.unhideLockIcon_();
// Could be though that they've closed the warning dialog
if (this.messageShowing_)
@ -327,28 +324,6 @@ PROT_PhishMsgDisplayerBase.prototype.removeIfExists_ = function(orig,
return orig;
}
/**
* We don't want to confuse users if they land on a phishy page that uses
* SSL, so ensure that the lock icon never shows when we're showing our
* warning.
*/
PROT_PhishMsgDisplayerBase.prototype.hideLockIcon_ = function() {
var lockIcon = this.doc_.getElementById("lock-icon");
if (!lockIcon)
return;
lockIcon.hidden = true;
}
/**
* Ensure they can see it after our warning is finished.
*/
PROT_PhishMsgDisplayerBase.prototype.unhideLockIcon_ = function() {
var lockIcon = this.doc_.getElementById("lock-icon");
if (!lockIcon)
return;
lockIcon.hidden = false;
}
/**
* This method makes our warning icon visible in the location bar. It will
* be removed only when the problematic document is navigated awy from
@ -557,26 +532,7 @@ PROT_PhishMsgDisplayerCanvas.inherits(PROT_PhishMsgDisplayerBase);
* Displays the warning message. First we make sure the overlay is loaded
* then call showMessageAfterOverlay_.
*/
PROT_PhishMsgDisplayerCanvas.prototype.showMessage_ = function() {
G_Debug(this, "Showing message.");
// Load the overlay if we haven't already.
var dimmer = this.doc_.getElementById('safebrowsing-dim-area-canvas');
if (!dimmer) {
var onOverlayMerged = BindToObject(this.showMessageAfterOverlay_,
this);
var observer = new G_ObserverWrapper("xul-overlay-merged",
onOverlayMerged);
this.doc_.loadOverlay(
"chrome://browser/content/safebrowsing/warning-overlay.xul",
observer);
} else {
// The overlay is already loaded so we go ahead and call
// showMessageAfterOverlay_.
this.showMessageAfterOverlay_();
}
}
PROT_PhishMsgDisplayerCanvas.prototype.showMessage_ = function() { }
/**
* This does the actual work of showing the warning message.
@ -703,34 +659,7 @@ PROT_PhishMsgDisplayerCanvas.prototype.isVisibleElement_ = function(elt) {
/**
* Hide the warning message from the user.
*/
PROT_PhishMsgDisplayerCanvas.prototype.hideMessage_ = function() {
G_Debug(this, "Hiding phishing warning.");
G_Assert(this, this.messageShowing_, "Hide message called but not showing?");
this.messageShowing_ = false;
this.repainter_.cancel();
this.repainter_ = null;
// Hide the warning popup.
var message = this.doc_.getElementById(this.messageId_);
message.hidden = true;
message.style.display = "none";
var content = this.doc_.getElementById(this.messageContentId_);
content.style.height = "";
content.style.overflow = "";
var tail = this.doc_.getElementById(this.messageTailId_);
tail.hidden = true;
tail.style.display = "none";
// Remove the canvas element from the chrome document.
var pageCanvas = this.doc_.getElementById(this.pageCanvasId_);
pageCanvas.parentNode.removeChild(pageCanvas);
// Hide the dimmer.
var dimarea = this.doc_.getElementById(this.dimAreaId_);
dimarea.hidden = true;
}
PROT_PhishMsgDisplayerCanvas.prototype.hideMessage_ = function() { }
/**

Просмотреть файл

@ -3,4 +3,5 @@ browser.jar:
* content/browser/safebrowsing/sb-loader.js (content/sb-loader.js)
+ content/browser/safebrowsing/warning-overlay.xul (content/warning-overlay.xul)
+ content/browser/safebrowsing/report-phishing-overlay.xul (content/report-phishing-overlay.xul)
+ content/browser/safebrowsing/blockedSite.xhtml (content/blockedSite.xhtml)
% overlay chrome://browser/content/browser.xul chrome://browser/content/safebrowsing/report-phishing-overlay.xul

Просмотреть файл

@ -61,6 +61,13 @@ SafebrowsingApplicationMod.prototype.registerSelf = function(compMgr, fileSpec,
fileSpec,
loc,
type);
compMgr.registerFactoryLocation(this.cid,
"UrlClassifier Blocked Error Page",
"@mozilla.org/network/protocol/about;1?what=blocked",
fileSpec,
loc,
type);
};
SafebrowsingApplicationMod.prototype.getClassObject = function(compMgr, cid, iid) {

Просмотреть файл

@ -1979,7 +1979,11 @@ SessionStoreService.prototype = {
var cr = Cc["@mozilla.org/xre/app-info;1"].getService(Ci.nsICrashReporter);
cr.annotateCrashReport("URL", currentUrl);
}
catch (ex) { debug(ex); }
catch (ex) {
// don't make noise when crashreporter is built but not enabled
if (ex.result != Components.results.NS_ERROR_NOT_INITIALIZED)
debug(ex);
}
},
/**

Просмотреть файл

@ -35,9 +35,9 @@
# ***** END LICENSE BLOCK *****
# Required Plugins:
# SetVistaDefaultApp http://nsis.sourceforge.net/SetVistaDefaultApp_plug-in
# ShellLink http://nsis.sourceforge.net/ShellLink_plug-in
# UAC http://nsis.sourceforge.net/UAC_plug-in
# AppAssocReg http://nsis.sourceforge.net/Application_Association_Registration_plug-in
# ShellLink http://nsis.sourceforge.net/ShellLink_plug-in
# UAC http://nsis.sourceforge.net/UAC_plug-in
; Set verbosity to 3 (e.g. no script) to lessen the noise in the build logs
!verbose 3
@ -110,14 +110,18 @@ VIAddVersionKey "FileDescription" "${BrandShortName} Installer"
!insertmacro _LoggingCommon
!insertmacro AddDDEHandlerValues
!insertmacro ChangeMUIHeaderImage
!insertmacro CloseApp
!insertmacro CreateRegKey
!insertmacro GetPathFromString
!insertmacro GetParent
!insertmacro IsHandlerForInstallDir
!insertmacro ManualCloseAppPrompt
!insertmacro RegCleanAppHandler
!insertmacro RegCleanMain
!insertmacro RegCleanUninstall
!insertmacro SetBrandNameVars
!insertmacro UnloadUAC
!insertmacro WriteRegStr2
!insertmacro WriteRegDWORD2
@ -129,6 +133,7 @@ VIAddVersionKey "FileDescription" "${BrandShortName} Installer"
!insertmacro InstallOnInitCommon
!insertmacro InstallStartCleanupCommon
!insertmacro LeaveDirectoryCommon
!insertmacro OnEndCommon
!insertmacro PreDirectoryCommon
Name "${BrandFullName}"
@ -164,9 +169,11 @@ ReserveFile summary.ini
* Installation Pages
*/
; Welcome Page
!define MUI_PAGE_CUSTOMFUNCTION_PRE preWelcome
!insertmacro MUI_PAGE_WELCOME
; License Page
!define MUI_PAGE_CUSTOMFUNCTION_SHOW showLicense
!define MUI_LICENSEPAGE_CHECKBOX
!insertmacro MUI_PAGE_LICENSE license.rtf
@ -217,7 +224,7 @@ Section "-InstallStartCleanup"
DetailPrint $(STATUS_CLEANUP)
SetDetailsPrint none
SetOutPath $INSTDIR
SetOutPath "$INSTDIR"
${StartInstallLog} "${BrandFullName}" "${AB_CD}" "${AppVersion}" "${GREVersion}"
; Try to delete the app's main executable and if we can't delete it try to
@ -229,8 +236,8 @@ Section "-InstallStartCleanup"
; Create a temporary backup directory.
GetTempFileName $TmpVal "$TEMP"
${DeleteFile} $TmpVal
SetOutPath $TmpVal
${DeleteFile} "$TmpVal"
SetOutPath "$TmpVal"
${If} ${FileExists} "$INSTDIR\${FileMainEXE}"
ClearErrors
@ -266,7 +273,7 @@ Section "-InstallStartCleanup"
StrCpy $R1 "xpicleanup.exe"
Call CheckInUse
SetOutPath $INSTDIR
SetOutPath "$INSTDIR"
RmDir /r "$TmpVal"
ClearErrors
@ -389,6 +396,11 @@ Section "-Application" APP_IDX
StrCpy $TmpVal "HKLM" ; used primarily for logging
${RegCleanMain} "Software\Mozilla"
${RegCleanUninstall}
ReadRegStr $0 HKLM "Software\mozilla.org\Mozilla" "CurrentVersion"
${If} "$0" != "${GREVersion}"
WriteRegStr HKLM "Software\mozilla.org\Mozilla" "CurrentVersion" "${GREVersion}"
${EndIf}
${EndIf}
${RemoveDeprecatedKeys}
@ -533,8 +545,9 @@ Function CheckInUse
MessageBox MB_RETRYCANCEL|MB_ICONQUESTION "$0" IDRETRY retry
Delete "$TmpVal\$R1"
CopyFiles /SILENT "$TmpVal\*" "$INSTDIR\"
SetOutPath $INSTDIR
SetOutPath "$INSTDIR"
RmDir /r "$TmpVal"
${OnEndCommon}
Quit
${EndIf}
${EndIf}
@ -612,19 +625,16 @@ Function CopyFile
FunctionEnd
Function LaunchApp
ClearErrors
${GetParameters} $0
${If} $0 != ""
ClearErrors
${GetOptions} "$0" "/UAC:" $1
${Unless} ${Errors}
GetFunctionAddress $0 LaunchAppFromElevatedProcess
UAC::ExecCodeSegment $0
Quit
${EndUnless}
${GetOptions} "$0" "/UAC:" $1
${If} ${Errors}
${ManualCloseAppPrompt} "${WindowClass}" "$(WARN_MANUALLY_CLOSE_APP_LAUNCH)"
Exec "$INSTDIR\${FileMainEXE}"
${Else}
GetFunctionAddress $0 LaunchAppFromElevatedProcess
UAC::ExecCodeSegment $0
${EndIf}
${ManualCloseAppPrompt} "${WindowClass}" "$(WARN_MANUALLY_CLOSE_APP_LAUNCH)"
Exec "$INSTDIR\${FileMainEXE}"
FunctionEnd
Function LaunchAppFromElevatedProcess
@ -635,6 +645,10 @@ Function LaunchAppFromElevatedProcess
${StrFilter} "${FileMainEXE}" "+" "" "" $R9
ReadRegStr $0 HKLM "Software\Clients\StartMenuInternet\$R9\DefaultIcon" ""
${GetPathFromString} "$0" $0
${GetParent} "$0" $1
; Set our current working directory to the application's install directory
; otherwise the 7-Zip temp directory will be in use and won't be deleted.
SetOutPath "$1"
Exec "$0"
FunctionEnd
@ -653,7 +667,23 @@ FunctionEnd
BrandingText " "
################################################################################
# Page pre and leave functions
# Page pre, show, and leave functions
Function preWelcome
${If} ${FileExists} "$EXEDIR\localized\distribution\modern-wizard.bmp"
Delete "$PLUGINSDIR\modern-wizard.bmp"
CopyFiles /SILENT "$EXEDIR\localized\distribution\modern-wizard.bmp" "$PLUGINSDIR\modern-wizard.bmp"
${EndIf}
FunctionEnd
Function showLicense
${If} ${FileExists} "$EXEDIR\localized\distribution\modern-header.bmp"
${AndIf} $hHeaderBitmap == ""
Delete "$PLUGINSDIR\modern-header.bmp"
CopyFiles /SILENT "$EXEDIR\localized\distribution\modern-header.bmp" "$PLUGINSDIR\modern-header.bmp"
${ChangeMUIHeaderImage} "$PLUGINSDIR\modern-header.bmp"
${EndIf}
FunctionEnd
Function preOptions
!insertmacro MUI_HEADER_TEXT "$(OPTIONS_PAGE_TITLE)" "$(OPTIONS_PAGE_SUBTITLE)"
@ -758,6 +788,9 @@ FunctionEnd
# Initialization Functions
Function .onInit
StrCpy $LANGUAGE 0
${SetBrandNameVars} "$EXEDIR\localized\distribution\setup.ini"
${InstallOnInitCommon} "$(WARN_UNSUPPORTED_MSG)"
!insertmacro MUI_INSTALLOPTIONS_EXTRACT "options.ini"
@ -768,8 +801,6 @@ Function .onInit
!insertmacro createComponentsINI
!insertmacro createShortcutsINI
StrCpy $LANGUAGE 0
; There must always be nonlocalized and localized directories.
${GetSize} "$EXEDIR\nonlocalized\" "/S=0K" $R5 $R7 $R8
${GetSize} "$EXEDIR\localized\" "/S=0K" $R6 $R7 $R8
@ -784,12 +815,12 @@ Function .onInit
; Hide DOMi in the components page if it isn't available.
SectionSetText ${DOMI_IDX} ""
${EndIf}
; Initialize $hHeaderBitmap to prevent redundant changing of the bitmap if
; the user clicks the back button
StrCpy $hHeaderBitmap ""
FunctionEnd
Function .OnInstFailed
UAC::Unload
FunctionEnd
Function .OnInstSuccess
UAC::Unload
Function .onGUIEnd
${OnEndCommon}
FunctionEnd

Просмотреть файл

@ -55,6 +55,11 @@
${SetStartMenuInternet}
${FixShellIconHandler}
${SetUninstallKeys}
ReadRegStr $0 HKLM "Software\mozilla.org\Mozilla" "CurrentVersion"
${If} "$0" != "${GREVersion}"
WriteRegStr HKLM "Software\mozilla.org\Mozilla" "CurrentVersion" "${GREVersion}"
${EndIf}
${EndIf}
${RemoveDeprecatedKeys}
@ -110,7 +115,7 @@
; Only register as the handler on Vista if the app registry name exists
; under the RegisteredApplications registry key.
${Unless} ${Errors}
SetVistaDefaultApp::SetAsDefault "${AppRegName}"
AppAssocReg::SetAppAsDefaultAll "${AppRegName}"
${EndUnless}
${EndIf}
!endif

Просмотреть файл

@ -35,9 +35,9 @@
# ***** END LICENSE BLOCK *****
# Required Plugins:
# SetVistaDefaultApp http://nsis.sourceforge.net/SetVistaDefaultApp_plug-in
# ShellLink http://nsis.sourceforge.net/ShellLink_plug-in
# UAC http://nsis.sourceforge.net/UAC_plug-in
# AppAssocReg http://nsis.sourceforge.net/Application_Association_Registration_plug-in
# ShellLink http://nsis.sourceforge.net/ShellLink_plug-in
# UAC http://nsis.sourceforge.net/UAC_plug-in
; Set verbosity to 3 (e.g. no script) to lessen the noise in the build logs
!verbose 3
@ -62,10 +62,10 @@ Var TmpVal
; The following includes are provided by NSIS.
!include FileFunc.nsh
!include LogicLib.nsh
!include MUI.nsh
!include TextFunc.nsh
!include WinMessages.nsh
!include WordFunc.nsh
!include MUI.nsh
; WinVer.nsh was added in the same release that RequestExecutionLevel so check
; if ___WINVER__NSH___ is defined to determine if RequestExecutionLevel is
@ -74,7 +74,7 @@ Var TmpVal
!ifdef ___WINVER__NSH___
RequestExecutionLevel user
!else
!warning "Uninstaller will be created without Vista compatibility.$\n \
!warning "Installer will be created without Vista compatibility.$\n \
Upgrade your NSIS installation to at least version 2.22 to resolve."
!endif
@ -104,10 +104,13 @@ VIAddVersionKey "FileDescription" "${BrandShortName} Helper"
!insertmacro RegCleanAppHandler
!insertmacro RegCleanMain
!insertmacro RegCleanUninstall
!insertmacro UnloadUAC
!insertmacro WriteRegDWORD2
!insertmacro WriteRegStr2
!insertmacro un.ChangeMUIHeaderImage
!insertmacro un.CleanVirtualStore
!insertmacro un.DeleteRelativeProfiles
!insertmacro un.GetLongPath
!insertmacro un.GetSecondInstallPath
!insertmacro un.ManualCloseAppPrompt
@ -118,12 +121,16 @@ VIAddVersionKey "FileDescription" "${BrandShortName} Helper"
!insertmacro un.RegCleanUninstall
!insertmacro un.RegCleanProtocolHandler
!insertmacro un.RemoveQuotesFromPath
!insertmacro un.SetBrandNameVars
!include shared.nsh
; Helper macros for ui callbacks. Insert these after shared.nsh
!insertmacro OnEndCommon
!insertmacro UninstallOnInitCommon
!insertmacro un.OnEndCommon
Name "${BrandFullName}"
OutFile "helper.exe"
InstallDirRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\${BrandFullNameInternal} (${AppVersion})" "InstallLocation"
@ -152,11 +159,11 @@ ShowUnInstDetails nevershow
* Uninstall Pages
*/
; Welcome Page
!define MUI_PAGE_CUSTOMFUNCTION_PRE un.preWelcome
!insertmacro MUI_UNPAGE_WELCOME
; Uninstall Confirm Page
!define MUI_PAGE_CUSTOMFUNCTION_LEAVE un.leaveConfirm
!insertmacro MUI_UNPAGE_CONFIRM
UninstPage custom un.preConfirm un.leaveConfirm
; Remove Files Page
!insertmacro MUI_UNPAGE_INSTFILES
@ -201,6 +208,11 @@ Section "Uninstall"
ClearErrors
${EndIf}
${MUI_INSTALLOPTIONS_READ} $0 "unconfirm.ini" "Field 3" "State"
${If} "$0" == "1"
${un.DeleteRelativeProfiles} "Mozilla\Firefox"
${EndIf}
SetShellVarContext current ; Set SHCTX to HKCU
${un.RegCleanMain} "Software\Mozilla"
${un.RegCleanUninstall}
@ -354,10 +366,50 @@ FunctionEnd
BrandingText " "
################################################################################
# Page pre and leave functions
# Page pre, show, and leave functions
Function un.preWelcome
${If} ${FileExists} "$INSTDIR\distribution\modern-wizard.bmp"
Delete "$PLUGINSDIR\modern-wizard.bmp"
CopyFiles /SILENT "$INSTDIR\distribution\modern-wizard.bmp" "$PLUGINSDIR\modern-wizard.bmp"
${EndIf}
FunctionEnd
Function un.preConfirm
${If} ${FileExists} "$INSTDIR\distribution\modern-header.bmp"
${AndIf} $hHeaderBitmap == ""
Delete "$PLUGINSDIR\modern-header.bmp"
CopyFiles /SILENT "$INSTDIR\distribution\modern-header.bmp" "$PLUGINSDIR\modern-header.bmp"
${un.ChangeMUIHeaderImage} "$PLUGINSDIR\modern-header.bmp"
${EndIf}
!insertmacro un.createUnConfirmINI
!insertmacro MUI_HEADER_TEXT "$(UN_CONFIRM_PAGE_TITLE)" "$(UN_CONFIRM_PAGE_SUBTITLE)"
; The Summary custom page has a textbox that will automatically receive
; focus. This sets the focus to the Install button instead.
!insertmacro MUI_INSTALLOPTIONS_INITDIALOG "unconfirm.ini"
GetDlgItem $0 $HWNDPARENT 1
${MUI_INSTALLOPTIONS_READ} $1 "unconfirm.ini" "Field 4" "HWND"
SetCtlColors $1 0x000000 0xFFFFEE
ShowWindow $1 ${SW_HIDE}
System::Call "user32::SetFocus(i r0, i 0x0007, i,i)i"
!insertmacro MUI_INSTALLOPTIONS_SHOW
FunctionEnd
; Checks if the app being uninstalled is running.
Function un.leaveConfirm
${MUI_INSTALLOPTIONS_READ} $0 "unconfirm.ini" "Settings" "State"
StrCmp $0 "3" +1 continue
${MUI_INSTALLOPTIONS_READ} $0 "unconfirm.ini" "Field 3" "State"
${MUI_INSTALLOPTIONS_READ} $1 "unconfirm.ini" "Field 4" "HWND"
StrCmp $0 1 +1 +3
ShowWindow $1 ${SW_SHOW}
Abort
ShowWindow $1 ${SW_HIDE}
Abort
continue:
; Try to delete the app executable and if we can't delete it try to find the
; app's message window and prompt the user to close the app. This allows
; running an instance that is located in another directory. If for whatever
@ -415,5 +467,19 @@ Function un.onInit
${Unless} ${FileExists} "$INSTDIR\${FileMainEXE}"
Abort
${EndUnless}
StrCpy $LANGUAGE 0
${un.SetBrandNameVars} "$INSTDIR\distribution\setup.ini"
; Initialize $hHeaderBitmap to prevent redundant changing of the bitmap if
; the user clicks the back button
StrCpy $hHeaderBitmap ""
FunctionEnd
Function .onGUIEnd
${OnEndCommon}
FunctionEnd
Function un.onGUIEnd
${un.OnEndCommon}
FunctionEnd

Просмотреть файл

@ -193,6 +193,10 @@ include $(call EXPAND_LOCALE_SRCDIR,toolkit/locales)/installer/windows/charset.m
repackage-win32-installer: WIN32_INSTALLER_OUT=$(_ABS_DIST)/install/sea/$(PKG_BASENAME).installer.exe
repackage-win32-installer: $(WIN32_INSTALLER_IN) $(SUBMAKEFILES)
ifneq (en-US,$(AB_CD))
@echo "Verifying $(AB_CD) installer variable usage"
@$(PERL) $(topsrcdir)/toolkit/mozapps/installer/windows/nsis/check-locales.pl $(LOCALE_SRCDIR)/installer
endif
@echo "Repackaging $(WIN32_INSTALLER_IN) into $(WIN32_INSTALLER_OUT)."
ifdef MOZ_BRANDING_DIRECTORY
$(MAKE) -C $(DEPTH)/$(MOZ_BRANDING_DIRECTORY) export

Просмотреть файл

@ -273,19 +273,19 @@
<!ENTITY thisFrameMenu.label "This Frame">
<!ENTITY thisFrameMenu.accesskey "h">
<!ENTITY textZoomEnlargeCmd.label "Increase">
<!ENTITY textZoomEnlargeCmd.accesskey "I">
<!ENTITY textZoomEnlargeCmd.commandkey "+">
<!ENTITY textZoomEnlargeCmd.commandkey2 "="> <!-- + is above this key on many keyboards -->
<!ENTITY fullZoomEnlargeCmd.label "Zoom In">
<!ENTITY fullZoomEnlargeCmd.accesskey "I">
<!ENTITY fullZoomEnlargeCmd.commandkey "+">
<!ENTITY fullZoomEnlargeCmd.commandkey2 "="> <!-- + is above this key on many keyboards -->
<!ENTITY textZoomReduceCmd.label "Decrease">
<!ENTITY textZoomReduceCmd.accesskey "D">
<!ENTITY textZoomReduceCmd.commandkey "-">
<!ENTITY textZoomResetCmd.commandkey "0">
<!ENTITY textZoomResetCmd.label "Normal">
<!ENTITY textZoomResetCmd.accesskey "N">
<!ENTITY textSize.label "Text Size">
<!ENTITY textSize.accesskey "z">
<!ENTITY fullZoomReduceCmd.label "Zoom Out">
<!ENTITY fullZoomReduceCmd.accesskey "O">
<!ENTITY fullZoomReduceCmd.commandkey "-">
<!ENTITY fullZoomResetCmd.commandkey "0">
<!ENTITY fullZoomResetCmd.label "Reset">
<!ENTITY fullZoomResetCmd.accesskey "R">
<!ENTITY fullZoom.label "Zoom">
<!ENTITY fullZoom.accesskey "Z">
<!ENTITY newTabButton.tooltip "Open a new tab">
<!ENTITY newWindowButton.tooltip "Open a new window">
@ -345,3 +345,5 @@
<!ENTITY editBookmark.done.label "Done">
<!ENTITY editBookmark.delete.label "Delete">
<!ENTITY identity.moreInfoLinkText "Tell me more about this web site...">

Просмотреть файл

@ -83,12 +83,23 @@ refreshBlocked.goButton.accesskey=A
refreshBlocked.refreshLabel=%S prevented this page from automatically reloading.
refreshBlocked.redirectLabel=%S prevented this page from automatically redirecting to another page.
# Chromeless popup handling
chromelessWindow.warningMessage=The web site at %S has hidden your toolbars.
chromelessWindow.warningNoLocation=This web site has hidden your toolbars.
chromelessWindow.showToolbarsButton=Show Toolbars
chromelessWindow.accessKey=S
# Star button
starButtonOn.tooltip=Edit this bookmark
starButtonOff.tooltip=Bookmark this page
# Identity information
identity.domainverified.title=Location Verified
identity.domainverified.body=You are currently visiting:
identity.domainverified.supplemental=Information identifying the owner of this web site may not have been validated.
identity.identified.title=Identity Verified
identity.identified.body=This web site is owned by:
identity.identified.verifier=Verified by: %S
identity.identified.state_and_country=%S, %S
identity.identified.title_with_country=%S (%S)
identity.unknown.title=Identity Unknown
identity.unknown.body=This web site does not supply identity information.
identity.encrypted=Your connection to this web site is encrypted to prevent eavesdropping.
identity.unencrypted=Your connection to this web site is not encrypted.

Просмотреть файл

@ -4,7 +4,7 @@
<!-- When making changes to prefWindow.styleWin test both Windows Classic and
Luna since widget heights are different based on the OS theme -->
<!ENTITY prefWin.styleWin "width: 42em; min-height: 44em;">
<!ENTITY prefWindow.styleMac "width: 47em;">
<!ENTITY prefWin.styleMac "width: 47em; min-height: 45em;">
<!ENTITY prefWin.styleGNOME "width: 42em; min-height: 44.5em;">
<!ENTITY paneMain.title "Main">

Просмотреть файл

@ -0,0 +1,11 @@
malware.title=Suspected Attack Site!
malware.shortDesc=The web site at %S has been reported as an attack site and has been blocked based on your security preferences.
malware.longDesc=<p>Attack sites try to install programs that steal private information, use your computer to attack others, or damage your system.</p>\n<p>Web site owners who believe their site has been reported as an attack site in error may <a href='http://www.stopbadware.org/home/reviewinfo' >request a review</a>.</p>
phishing.title=Suspected Web Forgery!
phishing.shortDesc=The web site at %S has been reported as a web forgery designed to trick users into sharing personal or financial information.
phishing.longDesc=<p>Entering any personal information on this page may result in identity theft or other fraud.</p><p>These types of web forgeries are used in scams known as phishing attacks, in which fraudulent web pages and emails are used to imitate sources you may trust.</p>
# Localization note (phishing.learnMoreLink): please leave the <a id="faqLink" href=""> text
# as-is. A localized href is pulled in from user preferences automatically.
phishing.learnMoreLink=<p>You can find out more about <a id="faqLink" href="">how %S protects you</a> from phishing attacks.</p>

Просмотреть файл

@ -60,3 +60,4 @@ externalProtocolUnknown=<Unknown>
externalProtocolChkMsg=Remember my choice for all links of this type.
externalProtocolLaunchBtn=Launch application
malwareBlocked=The site at %S has been reported as an attack site and has been blocked based on your security preferences.
phishingBlocked=The web site at %S has been reported as a web forgery designed to trick users into sharing personal or financial information.

Просмотреть файл

@ -123,6 +123,17 @@
</ul>
">
<!ENTITY nssBadCert.title "Secure Connection Failed">
<!ENTITY nssBadCert.longDesc "
<ul>
<li>This could be a problem with the server's configuration, or it could be
someone trying to impersonate the server.</li>
<li>If you have connected to this server successfully in the past, the error may
be temporary, and you can try again later.</li>
<li>You can see and change your current list of servers with known security problems
in your advanced encryption settings.</li>
</ul>
">
<!ENTITY sharedLongDesc "
<ul>
@ -140,3 +151,9 @@
<p>Attack sites try to install programs that steal private information, use your computer to attack others, or damage your system.</p>
<p>Web site owners who believe their site has been reported as an attack site in error may <a href='http://www.stopbadware.org/home/reviewinfo' >request a review</a>.</p>
">
<!ENTITY phishingBlocked.title "Suspected Web Forgery!">
<!ENTITY phishingBlocked.longDesc "
<p>Entering any personal information on this page may result in identity theft or other fraud.</p>
<p>These types of web forgeries are used in scams known as phishing attacks, in which fraudulent web pages and emails are used to imitate sources you may trust.</p>
">

Просмотреть файл

@ -41,60 +41,68 @@
# Accesskeys are defined by prefixing the letter that is to be used for the
# accesskey with an ampersand (e.g. &).
# Do not replace ${BrandShortName} or ${BrandFullName} with a custom string.
# Do not replace $BrandShortName, $BrandFullName, or $BrandFullNameDA with a
# custom string and always use the same one as used by the en-US files.
# $BrandFullNameDA allows the string to contain an ampersand (e.g. DA stands
# for double ampersand) and prevents the letter following the ampersand from
# being used as an accesskey.
# You can use \n to create a newline in the string but only when the string
# from en-US contains a \n.
REG_APP_DESC=${BrandShortName} delivers safe, easy web browsing. A familiar user interface, enhanced security features including protection from online identity theft, and integrated search let you get the most out of the web.
REG_APP_DESC=$BrandShortName delivers safe, easy web browsing. A familiar user interface, enhanced security features including protection from online identity theft, and integrated search let you get the most out of the web.
OPTIONAL_COMPONENTS_TITLE=Choose Optional Components
OPTIONAL_COMPONENTS_SUBTITLE=Choose which features of $(^NameDA) you want to install.
OPTIONAL_COMPONENTS_SUBTITLE=Choose which features of $BrandShortName you want to install.
OPTIONAL_COMPONENTS_LABEL=Optional Components:
APP_DESC=Required files for the ${BrandShortName} application
DOMI_TITLE=DOM Inspector
DOMI_TEXT=Inspects the structure and properties of a window and its contents.
QFA_TITLE=Quality Feedback Agent
QFA_TEXT=Sends information about program crashes to Mozilla.
CONTEXT_OPTIONS=${BrandShortName} &Options
CONTEXT_SAFE_MODE=${BrandShortName} &Safe Mode
CONTEXT_OPTIONS=$BrandShortName &Options
CONTEXT_SAFE_MODE=$BrandShortName &Safe Mode
SAFE_MODE=Safe Mode
OPTIONS_PAGE_TITLE=Setup Type
OPTIONS_PAGE_SUBTITLE=Choose setup options
SHORTCUTS_PAGE_TITLE=Set Up Shortcuts
SHORTCUTS_PAGE_SUBTITLE=Create Program Icons
SUMMARY_PAGE_TITLE=Summary
SUMMARY_PAGE_SUBTITLE=Ready to start installing ${BrandShortName}
SUMMARY_INSTALLED_TO=${BrandShortName} will be installed to the following location:
SUMMARY_PAGE_SUBTITLE=Ready to start installing $BrandShortName
SUMMARY_INSTALLED_TO=$BrandShortName will be installed to the following location:
SUMMARY_CLICK=Click Install to continue.
SURVEY_TEXT=&Tell us what you thought of ${BrandShortName}
LAUNCH_TEXT=&Launch ${BrandFullName} now
WARN_APP_RUNNING_INSTALL=${BrandFullName} must be closed to proceed with the installation.\n\nClick "OK" to exit ${BrandFullName} automatically and continue.
CREATE_ICONS_DESC=Create icons for ${BrandShortName}:
SURVEY_TEXT=&Tell us what you thought of $BrandShortName
LAUNCH_TEXT=&Launch $BrandShortName now
WARN_APP_RUNNING_INSTALL=$BrandShortName must be closed to proceed with the installation.\n\nClick "OK" to exit $BrandShortName automatically and continue.
CREATE_ICONS_DESC=Create icons for $BrandShortName:
ICONS_DESKTOP=On my &Desktop
ICONS_STARTMENU=In my &Start Menu Programs folder
ICONS_QUICKLAUNCH=In my &Quick Launch bar
WARN_MANUALLY_CLOSE_APP_UNINSTALL=${BrandFullName} must be closed to proceed with the uninstall.\n\nPlease close ${BrandFullName} to continue.
WARN_MANUALLY_CLOSE_APP_LAUNCH=${BrandFullName} is already running.\n\nPlease close ${BrandFullName} prior to launching the version you have just installed.
WARN_MANUALLY_CLOSE_APP_UNINSTALL=$BrandShortName must be closed to proceed with the uninstall.\n\nPlease close $BrandShortName to continue.
WARN_MANUALLY_CLOSE_APP_LAUNCH=$BrandShortName is already running.\n\nPlease close $BrandShortName prior to launching the version you have just installed.
WARN_WRITE_ACCESS=You don't have access to write to the installation directory.\n\nClick OK to select a different directory.
WARN_DISK_SPACE=You don't have sufficient disk space to install to this location.\n\nClick OK to select a different location.
WARN_UNSUPPORTED_MSG=Sorry, ${BrandShortName} can't be installed. This version of ${BrandShortName} requires ${MinUnsupportedVer} or newer.
WARN_RESTART_REQUIRED_UNINSTALL=Your computer must be restarted to complete a previous uninstall of ${BrandShortName}. Do you want to reboot now?
WARN_UNSUPPORTED_MSG=Sorry, $BrandShortName can't be installed. This version of $BrandShortName requires ${MinUnsupportedVer} or newer.
WARN_RESTART_REQUIRED_UNINSTALL=Your computer must be restarted to complete a previous uninstall of $BrandShortName. Do you want to reboot now?
ERROR_CREATE_DIRECTORY=Error creating directory:\n\n$0\n\nClick Cancel to stop the installation or\nRetry to try again.
STATUS_INSTALL_APP=Installing ${BrandShortName}...
UN_CONFIRM_PAGE_TITLE=Uninstall $BrandFullName
UN_CONFIRM_PAGE_SUBTITLE=Remove $BrandFullName from your computer.
UN_CONFIRM_UNINSTALLED_FROM=$BrandShortName will be uninstalled from the following location:
UN_CONFIRM_CLICK=Click Uninstall to continue.
UN_REMOVE_PROFILES=&Remove my $BrandShortName personal data and customizations
UN_REMOVE_PROFILES_DESC=This will permanently remove your bookmarks, saved passwords, cookies and customizations. You may wish to keep this information if you plan on installing another version of $BrandShortName in the future.
STATUS_INSTALL_APP=Installing $BrandShortName...
STATUS_INSTALL_LANG=Installing Language Files (${AB_CD})...
STATUS_INSTALL_OPTIONAL=Installing Optional Components...
STATUS_UNINSTALL_MAIN=Uninstalling ${BrandShortName}...
STATUS_UNINSTALL_MAIN=Uninstalling $BrandShortName...
STATUS_CLEANUP=A Little Housekeeping...
# _DESC strings support approximately 65 characters per line.
# One line
OPTIONS_SUMMARY=Choose the type of setup you prefer, then click Next.
# One line
OPTION_STANDARD_DESC=${BrandShortName} will be installed with the most common options.
OPTION_STANDARD_DESC=$BrandShortName will be installed with the most common options.
OPTION_STANDARD_RADIO=&Standard
# One line
OPTION_COMPLETE_DESC=${BrandShortName} will be installed with all available options.
OPTION_COMPLETE_DESC=$BrandShortName will be installed with all available options.
OPTION_COMPLETE_RADIO=C&omplete
# Two lines
OPTION_CUSTOM_DESC=You may choose individual options to be installed. Recommended for experienced users.

Просмотреть файл

@ -44,54 +44,55 @@
# Accesskeys are defined by prefixing the letter that is to be used for the
# accesskey with an ampersand (e.g. &).
# Do not replace $(^NameDA) or $(^Name) with a custom string.
# Do not change $(^NameDA) to $(^Name) or $(^Name) to $(^NameDA). NameDA allows
# Name to contain an ampersand (e.g. DA stands for double ampersand) and
# prevents the letter following the ampersand being used as an accesskey.
# Do not replace $BrandShortName, $BrandFullName, or $BrandFullNameDA with a
# custom string and always use the same one as used by the en-US files.
# $BrandFullNameDA allows the string to contain an ampersand (e.g. DA stands
# for double ampersand) and prevents the letter following the ampersand from
# being used as an accesskey.
# You can use \n to create a newline in the string but only when the string
# from en-US contains a \n.
MUI_TEXT_WELCOME_INFO_TITLE=Welcome to the $(^NameDA) Setup Wizard
MUI_TEXT_WELCOME_INFO_TEXT=This wizard will guide you through the installation of $(^NameDA).\n\nIt is recommended that you close all other applications before starting Setup. This will make it possible to update relevant system files without having to reboot your computer.\n\n$_CLICK
MUI_TEXT_WELCOME_INFO_TITLE=Welcome to the $BrandFullNameDA Setup Wizard
MUI_TEXT_WELCOME_INFO_TEXT=This wizard will guide you through the installation of $BrandFullNameDA.\n\nIt is recommended that you close all other applications before starting Setup. This will make it possible to update relevant system files without having to reboot your computer.\n\n$_CLICK
MUI_TEXT_LICENSE_TITLE=License Agreement
MUI_TEXT_LICENSE_SUBTITLE=Please review the license terms before installing $(^NameDA).
MUI_TEXT_LICENSE_SUBTITLE=Please review the license terms before installing $BrandFullNameDA.
MUI_INNERTEXT_LICENSE_TOP=Press Page Down to see the rest of the agreement.
MUI_INNERTEXT_LICENSE_BOTTOM_CHECKBOX=If you accept the terms of the agreement, click the check box below. You must accept the agreement to install $(^NameDA). $_CLICK
MUI_INNERTEXT_LICENSE_BOTTOM_RADIOBUTTONS=If you accept the terms of the agreement, select the first option below. You must accept the agreement to install $(^NameDA). $_CLICK
MUI_INNERTEXT_LICENSE_BOTTOM_CHECKBOX=If you accept the terms of the agreement, click the check box below. You must accept the agreement to install $BrandFullNameDA. $_CLICK
MUI_INNERTEXT_LICENSE_BOTTOM_RADIOBUTTONS=If you accept the terms of the agreement, select the first option below. You must accept the agreement to install $BrandFullNameDA. $_CLICK
MUI_TEXT_COMPONENTS_TITLE=Choose Components
MUI_TEXT_COMPONENTS_SUBTITLE=Choose which features of $(^NameDA) you want to install.
MUI_TEXT_COMPONENTS_SUBTITLE=Choose which features of $BrandFullNameDA you want to install.
MUI_INNERTEXT_COMPONENTS_DESCRIPTION_TITLE=Description
MUI_INNERTEXT_COMPONENTS_DESCRIPTION_INFO=Position your mouse over a component to see its description.
MUI_TEXT_DIRECTORY_TITLE=Choose Install Location
MUI_TEXT_DIRECTORY_SUBTITLE=Choose the folder in which to install $(^NameDA).
MUI_TEXT_DIRECTORY_SUBTITLE=Choose the folder in which to install $BrandFullNameDA.
MUI_TEXT_INSTALLING_TITLE=Installing
MUI_TEXT_INSTALLING_SUBTITLE=Please wait while $(^NameDA) is being installed.
MUI_TEXT_INSTALLING_SUBTITLE=Please wait while $BrandFullNameDA is being installed.
MUI_TEXT_FINISH_TITLE=Installation Complete
MUI_TEXT_FINISH_SUBTITLE=Setup was completed successfully.
MUI_TEXT_ABORT_TITLE=Installation Aborted
MUI_TEXT_ABORT_SUBTITLE=Setup was not completed successfully.
MUI_BUTTONTEXT_FINISH=&Finish
MUI_TEXT_FINISH_INFO_TITLE=Completing the $(^NameDA) Setup Wizard
MUI_TEXT_FINISH_INFO_TEXT=$(^NameDA) has been installed on your computer.\n\nClick Finish to close this wizard.
MUI_TEXT_FINISH_INFO_REBOOT=Your computer must be restarted in order to complete the installation of $(^NameDA). Do you want to reboot now?
MUI_TEXT_FINISH_INFO_TITLE=Completing the $BrandFullNameDA Setup Wizard
MUI_TEXT_FINISH_INFO_TEXT=$BrandFullNameDA has been installed on your computer.\n\nClick Finish to close this wizard.
MUI_TEXT_FINISH_INFO_REBOOT=Your computer must be restarted in order to complete the installation of $BrandFullNameDA. Do you want to reboot now?
MUI_TEXT_FINISH_REBOOTNOW=Reboot now
MUI_TEXT_FINISH_REBOOTLATER=I want to manually reboot later
MUI_TEXT_STARTMENU_TITLE=Choose Start Menu Folder
MUI_TEXT_STARTMENU_SUBTITLE=Choose a Start Menu folder for the $(^NameDA) shortcuts.
MUI_TEXT_STARTMENU_SUBTITLE=Choose a Start Menu folder for the $BrandFullNameDA shortcuts.
MUI_INNERTEXT_STARTMENU_TOP=Select the Start Menu folder in which you would like to create the program's shortcuts. You can also enter a name to create a new folder.
MUI_TEXT_ABORTWARNING=Are you sure you want to quit $(^Name) Setup?
MUI_UNTEXT_WELCOME_INFO_TITLE=Welcome to the $(^NameDA) Uninstall Wizard
MUI_UNTEXT_WELCOME_INFO_TEXT=This wizard will guide you through the uninstallation of $(^NameDA).\n\nBefore starting the uninstallation, make sure $(^NameDA) is not running.\n\n$_CLICK
MUI_UNTEXT_CONFIRM_TITLE=Uninstall $(^NameDA)
MUI_UNTEXT_CONFIRM_SUBTITLE=Remove $(^NameDA) from your computer.
MUI_TEXT_ABORTWARNING=Are you sure you want to quit $BrandFullName Setup?
MUI_UNTEXT_WELCOME_INFO_TITLE=Welcome to the $BrandFullNameDA Uninstall Wizard
MUI_UNTEXT_WELCOME_INFO_TEXT=This wizard will guide you through the uninstallation of $BrandFullNameDA.\n\nBefore starting the uninstallation, make sure $BrandFullNameDA is not running.\n\n$_CLICK
MUI_UNTEXT_CONFIRM_TITLE=Uninstall $BrandFullNameDA
MUI_UNTEXT_CONFIRM_SUBTITLE=Remove $BrandFullNameDA from your computer.
MUI_UNTEXT_UNINSTALLING_TITLE=Uninstalling
MUI_UNTEXT_UNINSTALLING_SUBTITLE=Please wait while $(^NameDA) is being uninstalled.
MUI_UNTEXT_UNINSTALLING_SUBTITLE=Please wait while $BrandFullNameDA is being uninstalled.
MUI_UNTEXT_FINISH_TITLE=Uninstallation Complete
MUI_UNTEXT_FINISH_SUBTITLE=Uninstall was completed successfully.
MUI_UNTEXT_ABORT_TITLE=Uninstallation Aborted
MUI_UNTEXT_ABORT_SUBTITLE=Uninstall was not completed successfully.
MUI_UNTEXT_FINISH_INFO_TITLE=Completing the $(^NameDA) Uninstall Wizard
MUI_UNTEXT_FINISH_INFO_TEXT=$(^NameDA) has been uninstalled from your computer.\n\nClick Finish to close this wizard.
MUI_UNTEXT_FINISH_INFO_REBOOT=Your computer must be restarted in order to complete the uninstallation of $(^NameDA). Do you want to reboot now?
MUI_UNTEXT_ABORTWARNING=Are you sure you want to quit $(^Name) Uninstall?
MUI_UNTEXT_FINISH_INFO_TITLE=Completing the $BrandFullNameDA Uninstall Wizard
MUI_UNTEXT_FINISH_INFO_TEXT=$BrandFullNameDA has been uninstalled from your computer.\n\nClick Finish to close this wizard.
MUI_UNTEXT_FINISH_INFO_REBOOT=Your computer must be restarted in order to complete the uninstallation of $BrandFullNameDA. Do you want to reboot now?
MUI_UNTEXT_ABORTWARNING=Are you sure you want to quit $BrandFullName Uninstall?

Просмотреть файл

@ -41,11 +41,11 @@
# Accesskeys are defined by prefixing the letter that is to be used for the
# accesskey with an ampersand (e.g. &).
# Do not replace $(^NameDA) or $(^Name) with a custom string.
# Do not change $(^NameDA) to $(^Name) or $(^Name) to $(^NameDA). NameDA allows
# Name to contain an ampersand (e.g. DA stands for double ampersand) and
# prevents the letter following the ampersand being used as an accesskey.
# Do not replace $BrandShortName, $BrandFullName, or $BrandFullNameDA with a
# custom string and always use the same one as used by the en-US files.
# $BrandFullNameDA allows the string to contain an ampersand (e.g. DA stands
# for double ampersand) and prevents the letter following the ampersand from
# being used as an accesskey.
# You can use \n to create a newline in the string but only when the string
# from en-US contains a \n.
@ -55,8 +55,8 @@
# and end of a strong enclose the add and additional double quote to the
# beginning and end of the string (e.g. ""This will include quotes"").
SetupCaption=$(^Name) Setup
UninstallCaption=$(^Name) Uninstall
SetupCaption=$BrandFullName Setup
UninstallCaption=$BrandFullName Uninstall
BackBtn=< &Back
NextBtn=&Next >
AcceptBtn=I &accept the terms in the License Agreement
@ -71,15 +71,15 @@ ClickNext=Click Next to continue.
ClickInstall=Click Install to start the installation.
ClickUninstall=Click Uninstall to start the uninstallation.
Completed=Completed
LicenseTextRB=Please review the license agreement before installing $(^NameDA). If you accept all terms of the agreement, select the first option below. $_CLICK
LicenseTextRB=Please review the license agreement before installing $BrandFullNameDA. If you accept all terms of the agreement, select the first option below. $_CLICK
ComponentsText=Check the components you want to install and uncheck the components you don't want to install. $_CLICK
ComponentsSubText2_NoInstTypes=Select components to install:
DirText=Setup will install $(^NameDA) in the following folder. To install in a different folder, click Browse and select another folder. $_CLICK
DirText=Setup will install $BrandFullNameDA in the following folder. To install in a different folder, click Browse and select another folder. $_CLICK
DirSubText=Destination Folder
DirBrowseText=Select the folder to install $(^NameDA) in:
DirBrowseText=Select the folder to install $BrandFullNameDA in:
SpaceAvailable="Space available: "
SpaceRequired="Space required: "
UninstallingText=$(^NameDA) will be uninstalled from the following folder. $_CLICK
UninstallingText=$BrandFullNameDA will be uninstalled from the following folder. $_CLICK
UninstallingSubText=Uninstalling from:
FileError=Error opening file for writing: \r\n\r\n$0\r\n\r\nClick Abort to stop the installation,\r\nRetry to try again, or\r\nIgnore to skip this file.
FileError_NoIgnore=Error opening file for writing: \r\n\r\n$0\r\n\r\nClick Retry to try again, or\r\nCancel to stop the installation.

Просмотреть файл

@ -37,6 +37,7 @@
#ifdef MOZ_SAFE_BROWSING
locale/browser/safebrowsing/phishing-afterload-warning-message.dtd (%chrome/browser/safebrowsing/phishing-afterload-warning-message.dtd)
locale/browser/safebrowsing/report-phishing.dtd (%chrome/browser/safebrowsing/report-phishing.dtd)
locale/browser/safebrowsing/blockedSite.properties (%chrome/browser/safebrowsing/blockedSite.properties)
#endif
locale/browser/feeds/subscribe.dtd (%chrome/browser/feeds/subscribe.dtd)
locale/browser/feeds/subscribe.properties (%chrome/browser/feeds/subscribe.properties)

Просмотреть файл

@ -831,7 +831,7 @@ toolbar[iconsize="small"] #paste-button:hover:active {
#urlbar {
margin-top: 5px;
margin-bottom: 5px;
-moz-margin-start: 4px;
-moz-margin-start: 0px;
-moz-margin-end: 0px;
width: 7em;
min-width: 7em;
@ -839,33 +839,6 @@ toolbar[iconsize="small"] #paste-button:hover:active {
font: icon !important;
}
.formatted-url {
-moz-box-align: center;
margin: 0 3px;
/*XXX Gecko 1.9 quirk*/
-moz-padding-start: 1px;
color: -moz-fieldtext;
}
#urlbar[level="high"] .formatted-url ,
#urlbar[level="low"] .formatted-url {
color: black;
}
.formatted-url * {
margin: 0;
padding: 0;
cursor: text;
}
.formatted-url-ellipsis {
-moz-margin-start: 1px;
}
.formatted-url-prePath {
-moz-box-pack: center;
}
#urlbar[level="high"] > .autocomplete-textbox-container,
#urlbar[level="low"] > .autocomplete-textbox-container
{
@ -883,46 +856,6 @@ toolbar[iconsize="small"] #paste-button:hover:active {
background: url("chrome://browser/skin/Secure-background.gif") #FFFED8 repeat-x;
}
#urlbar #lock-icon {
height: 18px;
margin: -1px;
}
#urlbar[level="high"] #lock-icon {
list-style-image: url("chrome://browser/skin/Secure.png");
-moz-image-region: rect(0px, 18px, 18px, 0px);
}
#urlbar[level="high"] #lock-icon:hover {
-moz-image-region: rect(18px, 18px, 36px, 0px);
}
#urlbar[level="high"] #lock-icon:active {
-moz-image-region: rect(36px, 18px, 54px, 0px);
}
#urlbar[level="low"] #lock-icon {
list-style-image: url("chrome://browser/skin/Secure.png");
-moz-image-region: rect(0px, 18px, 18px, 0px);
}
#urlbar[level="low"] #lock-icon:hover {
-moz-image-region: rect(18px, 18px, 36px, 0px);
}
#urlbar[level="low"] #lock-icon:active {
-moz-image-region: rect(36px, 18px, 54px, 0px);
}
#urlbar[level="broken"] #lock-icon {
list-style-image: url("chrome://browser/skin/Security-broken.png");
-moz-image-region: rect(0px, 18px, 18px, 0px);
}
#urlbar[level="broken"] #lock-icon:hover {
-moz-image-region: rect(18px, 18px, 36px, 0px);
}
#urlbar[level="broken"] #lock-icon:active {
-moz-image-region: rect(36px, 18px, 54px, 0px);
}
#urlbar-container {
-moz-padding-end: 5px;
}
@ -1707,3 +1640,116 @@ toolbarbutton.bookmark-item[dragover="true"][open="true"] {
-moz-border-left-colors: ThreeDLightShadow ThreeDHighlight !important;
}
/* ::::: Identity Indicator Styling ::::: */
/* Location bar visuals*/
#identity-box {
/* Extend our margins out so that our highlight/separator bar covers the
location bar properly */
margin: -1px 0 -2px;
padding: 1px 2px 2px 0;
border-right: 1px solid #888;
background-color: white;
opacity: 0.9;
}
#identity-box:hover {
opacity: 1.0;
}
#identity-box.verifiedIdentity {
background-color: #BFA;
}
#urlbar[level="high"] > #identity-box,
#urlbar[level="low"] > #identity-box {
/* urlbar adds padding when security level is set, which we need to
counteract here so that we still fill the background. */
margin: -2px;
padding: 1px 2px 2px;
}
#identity-icon-label {
padding: 2px 2px 0;
margin: 0;
color: black;
vertical-align: middle;
}
.unknownIdentity > #identity-icon-label {
display: none;
}
/* Popup Icons */
#identity-popup-icon {
height: 64px;
width: 64px;
padding: 0;
margin: 10px 0 0;
list-style-image: url("chrome://browser/skin/identity.png");
-moz-image-region: rect(0px, 64px, 64px, 0px);
}
.verifiedDomain > #identity-popup-container > #identity-popup-icon {
-moz-image-region: rect(64px, 64px, 128px, 0px);
}
.verifiedIdentity > #identity-popup-container > #identity-popup-icon {
-moz-image-region: rect(128px, 64px, 192px, 0px);
}
/* Popup Title */
#identity-popup-title {
font-size: 120%;
font-weight: bold;
}
.verifiedIdentity > #identity-popup-title {
color: #6A6;
}
.unknownIdentity > #identity-popup-title {
color: #999;
}
.verifiedDomain > #identity-popup-title {
color: black;
}
/* Popup Body Text */
#identity-popup-content-box > description,
#identity-popup-encryption-label {
white-space: -moz-pre-wrap;
color: black;
padding-left: 10px;
}
#identity-popup-content {
padding-top: 5px;
margin-bottom: 0;
max-width: 200px;
}
.verifiedIdentity > #identity-popup-content,
.verifiedDomain > #identity-popup-content {
font-size: 140%;
font-weight: bold;
max-width: 300px;
}
#identity-popup-encryption {
margin: 10px 0;
}
.verifiedIdentity > #identity-popup-encryption > * > #identity-popup-encryption-icon,
.verifiedDomain > #identity-popup-encryption > * >#identity-popup-encryption-icon {
list-style-image: url("chrome://browser/skin/Secure.png");
-moz-image-region: rect(0px, 18px, 18px, 0px);
}
/* Popup Bounding Box */
#identity-popup-container {
background-image: none;
background-color: white;
min-width: 280px;
padding: 10px;
}

Просмотреть файл

@ -10,6 +10,7 @@ classic.jar:
skin/classic/browser/find.png
skin/classic/browser/find-bar-background.png
skin/classic/browser/Go.png
skin/classic/browser/identity.png
skin/classic/browser/Info.png
skin/classic/browser/page-livemarks.png
skin/classic/browser/livemark-item.png

Просмотреть файл

@ -1,3 +1,26 @@
/* Sidebars */
.sidebar-placesTree {
-moz-appearance: none;
border: 0;
margin: 0;
border-top: 1px solid ThreeDShadow;
}
.sidebar-placesTreechildren::-moz-tree-cell(leaf) ,
.sidebar-placesTreechildren::-moz-tree-image(leaf) {
cursor: pointer;
}
.sidebar-placesTreechildren::-moz-tree-cell-text(leaf, hover) {
cursor: pointer;
text-decoration: underline;
}
.sidebar-placesTreechildren::-moz-tree-cell(separator) {
cursor: default;
}
/* Toolbar */
#placesToolbar {
border-bottom: none;

Просмотреть файл

@ -856,7 +856,7 @@ toolbar[iconsize="small"] #paste-button:not([disabled="true"]):hover:active {
margin-bottom: 2px;
margin-top: 2px;
-moz-margin-end: 0px;
-moz-margin-start: 3px;
-moz-margin-start: 0px;
width: 7em;
min-width: 7em;
@ -868,33 +868,6 @@ toolbar[iconsize="small"] #paste-button:not([disabled="true"]):hover:active {
border-width: 1px;
}
.formatted-url {
-moz-box-align: center;
margin: 0 3px;
/*XXX Gecko 1.9 quirk*/
-moz-padding-start: 1px;
color: -moz-fieldtext;
}
#urlbar[level="high"] .formatted-url ,
#urlbar[level="low"] .formatted-url {
color: black;
}
.formatted-url * {
margin: 0;
padding: 0;
cursor: text;
}
.formatted-url-ellipsis {
-moz-margin-start: 1px;
}
.formatted-url-prePath {
-moz-box-pack: center;
}
#urlbar-container {
-moz-box-orient: horizontal;
-moz-box-align: stretch;
@ -1746,43 +1719,6 @@ toolbar[mode="text"] > #window-controls > toolbarbutton > .toolbarbutton-text {
color: #000000;
}
#urlbar[level="high"] #lock-icon {
-moz-image-region: rect(0px, 18px, 18px, 0px);
list-style-image: url("chrome://browser/skin/Secure.png");
}
#urlbar[level="high"] #lock-icon:hover {
-moz-image-region: rect(18px, 18px, 36px, 0px);
list-style-image: url("chrome://browser/skin/Secure.png");
}
#urlbar[level="high"] #lock-icon:active {
-moz-image-region: rect(36px, 18px, 54px, 0px);
list-style-image: url("chrome://browser/skin/Secure.png");
}
#urlbar[level="low"] #lock-icon {
-moz-image-region: rect(0px, 18px, 18px, 0px);
list-style-image: url("chrome://browser/skin/Secure.png");
}
#urlbar[level="low"] #lock-icon:hover {
-moz-image-region: rect(18px, 18px, 36px, 0px);
list-style-image: url("chrome://browser/skin/Secure.png");
}
#urlbar[level="low"] #lock-icon:active {
-moz-image-region: rect(36px, 18px, 54px, 0px);
list-style-image: url("chrome://browser/skin/Secure.png");
}
#urlbar[level="broken"] #lock-icon {
-moz-image-region: rect(0px, 18px, 18px, 0px);
list-style-image: url("chrome://browser/skin/Security-broken.png");
}
#urlbar[level="broken"] #lock-icon:hover {
-moz-image-region: rect(18px, 18px, 36px, 0px);
list-style-image: url("chrome://browser/skin/Security-broken.png");
}
#urlbar[level="broken"] #lock-icon:active {
-moz-image-region: rect(36px, 18px, 54px, 0px);
list-style-image: url("chrome://browser/skin/Security-broken.png");
}
%ifdef MOZ_WIDGET_GTK2
#urlbar > .autocomplete-textbox-container {
-moz-binding: url(chrome://browser/skin/browser.xml#autocomplete-security-wrapper);
@ -1895,3 +1831,117 @@ toolbarbutton.bookmark-item[dragover="true"][open="true"] {
.bookmark-item[dragover-bottom="true"] {
-moz-border-bottom-colors: #000000;
}
/* ::::: Identity Indicator Styling ::::: */
/* Location bar visuals*/
#identity-box {
cursor: help;
background-color: ThreeDFace;
%ifdef MOZ_WIDGET_GTK2
-moz-border-end: 1px solid ThreeDShadow;
%else
-moz-appearance: toolbox;
outline: 1px solid ThreeDShadow;
%endif
}
#identity-box.verifiedIdentity {
%ifdef MOZ_WIDGET_GTK2
border-color: highlight;
%else
outline-color: highlight;
%endif
}
#identity-box:hover {
%ifdef MOZ_WIDGET_GTK2
border-color: ThreeDDarkShadow;
%else
outline-color: ThreeDDarkShadow;
%endif
}
#identity-icon-label {
padding: 0 2px;
margin: 0;
cursor: inherit;
}
.unknownIdentity > #identity-icon-label {
display: none;
}
/* Popup Icons */
#identity-popup-icon {
height: 64px;
width: 64px;
padding: 0;
margin: 10px 0 0;
list-style-image: url("chrome://browser/skin/identity.png");
-moz-image-region: rect(0px, 64px, 64px, 0px);
}
.verifiedDomain > #identity-popup-container > #identity-popup-icon {
-moz-image-region: rect(64px, 64px, 128px, 0px);
}
.verifiedIdentity > #identity-popup-container > #identity-popup-icon {
-moz-image-region: rect(128px, 64px, 192px, 0px);
}
/* Popup Title */
#identity-popup-title {
font-size: 120%;
font-weight: bold;
}
.verifiedIdentity > #identity-popup-title {
color: #6A6;
}
.unknownIdentity > #identity-popup-title {
color: #999;
}
.verifiedDomain > #identity-popup-title {
color: black;
}
/* Popup Body Text */
#identity-popup-content-box > description,
#identity-popup-encryption-label {
white-space: -moz-pre-wrap;
color: black;
padding-left: 10px;
}
#identity-popup-content {
padding-top: 5px;
margin-bottom: 0;
max-width: 200px;
}
.verifiedIdentity > #identity-popup-content,
.verifiedDomain > #identity-popup-content {
font-size: 140%;
font-weight: bold;
max-width: 300px;
}
#identity-popup-encryption {
margin: 10px 0;
}
.verifiedIdentity > #identity-popup-encryption > * > #identity-popup-encryption-icon,
.verifiedDomain > #identity-popup-encryption > * >#identity-popup-encryption-icon {
list-style-image: url("chrome://browser/skin/Secure.png");
-moz-image-region: rect(0px, 18px, 18px, 0px);
}
/* Popup Bounding Box */
#identity-popup-container {
background-image: none;
background-color: white;
min-width: 280px;
padding: 10px;
}

Просмотреть файл

@ -6,6 +6,7 @@ classic.jar:
skin/classic/browser/endcap-bkgnd-hover.png
* skin/classic/browser/engineManager.css (engineManager.css)
skin/classic/browser/Info.png
skin/classic/browser/identity.png
skin/classic/browser/pageInfo.css
skin/classic/browser/pageInfo.png
skin/classic/browser/page-livemarks.png

Просмотреть файл

@ -1,15 +1,26 @@
/* Sidebars */
page > .placesTree > treechildren::-moz-tree-cell(leaf) ,
page > .placesTree > treechildren::-moz-tree-image(leaf) {
.sidebar-placesTree {
-moz-appearance: none;
border: 0;
margin: 0;
border-top: 1px solid ThreeDShadow;
}
.sidebar-placesTreechildren::-moz-tree-cell(leaf) ,
.sidebar-placesTreechildren::-moz-tree-image(leaf) {
cursor: pointer;
}
page > .placesTree > treechildren::-moz-tree-cell-text(leaf, hover) {
.sidebar-placesTreechildren::-moz-tree-cell-text(leaf, hover) {
cursor: pointer;
text-decoration: underline;
}
.sidebar-placesTreechildren::-moz-tree-cell(separator) {
cursor: default;
}
/* Toolbar */
#placesToolbar {
border: none;

Просмотреть файл

@ -284,9 +284,12 @@ interface nsIScriptSecurityManager : nsIXPCSecurityManager
/**
* Returns OK if aSourceURI and target have the same "origin"
* (scheme, host, and port).
* ReportError flag suppresses error reports for functions that
* don't need reporting.
*/
void checkSameOriginURI(in nsIURI aSourceURI,
in nsIURI aTargetURI);
in nsIURI aTargetURI,
in boolean reportError);
/**
* Returns OK if aSourcePrincipal and aTargetPrincipal

Просмотреть файл

@ -446,13 +446,8 @@ nsScriptSecurityManager::GetChannelPrincipal(nsIChannel* aChannel,
// OK, get the principal from the URI. Make sure this does the same thing
// as nsDocument::Reset and nsXULDocument::StartDocumentLoad.
nsCOMPtr<nsIURI> uri;
nsLoadFlags loadFlags = 0;
nsresult rv = aChannel->GetLoadFlags(&loadFlags);
if (NS_SUCCEEDED(rv) && (loadFlags & nsIChannel::LOAD_REPLACE)) {
aChannel->GetURI(getter_AddRefs(uri));
} else {
aChannel->GetOriginalURI(getter_AddRefs(uri));
}
nsresult rv = NS_GetFinalChannelURI(aChannel, getter_AddRefs(uri));
NS_ENSURE_SUCCESS(rv, rv);
return GetCodebasePrincipal(uri, aPrincipal);
}
@ -681,12 +676,15 @@ nsScriptSecurityManager::CheckSameOrigin(JSContext* cx,
NS_IMETHODIMP
nsScriptSecurityManager::CheckSameOriginURI(nsIURI* aSourceURI,
nsIURI* aTargetURI)
nsIURI* aTargetURI,
PRBool reportError)
{
if (!SecurityCompareURIs(aSourceURI, aTargetURI))
{
ReportError(nsnull, NS_LITERAL_STRING("CheckSameOriginError"),
if (reportError) {
ReportError(nsnull, NS_LITERAL_STRING("CheckSameOriginError"),
aSourceURI, aTargetURI);
}
return NS_ERROR_DOM_BAD_URI;
}
return NS_OK;

Просмотреть файл

@ -1,6 +1,6 @@
#!/usr/bin/python
NSPR_CO_TAG = 'NSPR_HEAD_20071009'
NSPR_CO_TAG = 'NSPR_HEAD_20071016'
NSS_CO_TAG = 'NSS_3_12_ALPHA_2'
NSPR_DIRS = ('nsprpub',)

Просмотреть файл

@ -1048,6 +1048,15 @@ ifdef NO_LD_ARCHIVE_FLAGS
SUB_SHLOBJS = $(SUB_LOBJS)
endif
ifdef HAVE_DTRACE
ifdef DTRACE_PROBE_OBJ
ifndef DTRACE_LIB_DEPENDENT
$(DTRACE_PROBE_OBJ): $(OBJS)
dtrace -G -C -32 -s $(MOZILLA_DTRACE_SRC) -o $(DTRACE_PROBE_OBJ) $(OBJS)
endif
endif
endif
# On Darwin (Mac OS X), dwarf2 debugging uses debug info left in .o files,
# so instead of deleting .o files after repacking them into a dylib, we make
# symlinks back to the originals. The symlinks are a no-op for stabs debugging,
@ -1078,17 +1087,17 @@ ifdef SHARED_LIBRARY_LIBS
@for lib in $(SHARED_LIBRARY_LIBS); do $(AR_EXTRACT) $${lib}; $(CLEANUP2); done
endif # SHARED_LIBRARY_LIBS
endif # NO_LD_ARCHIVE_FLAGS
ifdef NEED_DTRACE_PROBE_OBJ
ifdef DTRACE_LIB_DEPENDENT
@rm -f $(PROBE_LOBJS)
@for lib in $(MOZILLA_PROBE_LIBS); do $(AR_EXTRACT) $${lib}; $(CLEANUP2); done
dtrace -G -C -32 -s $(MOZILLA_DTRACE_SRC) -o $(NEED_DTRACE_PROBE_OBJ) $(PROBE_LOBJS)
dtrace -G -C -32 -s $(MOZILLA_DTRACE_SRC) -o $(DTRACE_PROBE_OBJ) $(PROBE_LOBJS)
@for lib in $(MOZILLA_PROBE_LIBS); do \
ofiles=`$(AR_LIST) $${lib}`; \
$(AR_DELETE) $${lib} $$ofiles; \
done
$(MKSHLIB) $(SHLIB_LDSTARTFILE) $(OBJS) $(LOBJS) $(SUB_SHLOBJS) $(NEED_DTRACE_PROBE_OBJ) $(PROBE_LOBJS) $(RESFILE) $(LDFLAGS) $(EXTRA_DSO_LDOPTS) $(OS_LIBS) $(EXTRA_LIBS) $(DEF_FILE) $(SHLIB_LDENDFILE)
$(MKSHLIB) $(SHLIB_LDSTARTFILE) $(OBJS) $(LOBJS) $(SUB_SHLOBJS) $(DTRACE_PROBE_OBJ) $(PROBE_LOBJS) $(RESFILE) $(LDFLAGS) $(EXTRA_DSO_LDOPTS) $(OS_LIBS) $(EXTRA_LIBS) $(DEF_FILE) $(SHLIB_LDENDFILE)
@rm -f $(PROBE_LOBJS)
@rm -f $(NEED_DTRACE_PROBE_OBJ)
@rm -f $(DTRACE_PROBE_OBJ)
@for lib in $(MOZILLA_PROBE_LIBS); do \
if [ -L $${lib} ]; then rm -f `readlink $${lib}`; fi; \
done
@ -1096,7 +1105,7 @@ ifdef NEED_DTRACE_PROBE_OBJ
else
$(MKSHLIB) $(SHLIB_LDSTARTFILE) $(OBJS) $(DTRACE_PROBE_OBJ) $(LOBJS) $(SUB_SHLOBJS) $(RESFILE) $(LDFLAGS) $(EXTRA_DSO_LDOPTS) $(OS_LIBS) $(EXTRA_LIBS) $(DEF_FILE) $(SHLIB_LDENDFILE)
endif # NEED_DTRACE_PROBE_OBJ
endif # DTRACE_LIB_DEPENDENT
ifeq (_WINNT,$(GNU_CC)_$(OS_ARCH))
ifdef MSMANIFEST_TOOL

Просмотреть файл

@ -557,6 +557,8 @@ public:
PRInt16* aImageBlockingStatus = nsnull);
/**
* Method to start an image load. This does not do any security checks.
* This method will attempt to make aURI immutable; a caller that wants to
* keep a mutable version around should pass in a clone.
*
* @param aURI uri of the image to be loaded
* @param aLoadingDocument the document we belong to
@ -750,42 +752,6 @@ public:
*/
static nsIContentPolicy *GetContentPolicy();
/**
* Make sure that whatever value *aPtr contains at any given moment is
* protected from JS GC until we remove the GC root. A call to this that
* succeeds MUST be matched by a call to RemoveJSGCRoot to avoid leaking.
*/
static nsresult AddJSGCRoot(jsval* aPtr, const char* aName) {
return AddJSGCRoot((void*)aPtr, aName);
}
/**
* Make sure that whatever object *aPtr is pointing to at any given moment is
* protected from JS GC until we remove the GC root. A call to this that
* succeeds MUST be matched by a call to RemoveJSGCRoot to avoid leaking.
*/
static nsresult AddJSGCRoot(JSObject** aPtr, const char* aName) {
return AddJSGCRoot((void*)aPtr, aName);
}
/**
* Make sure that whatever object *aPtr is pointing to at any given moment is
* protected from JS GC until we remove the GC root. A call to this that
* succeeds MUST be matched by a call to RemoveJSGCRoot to avoid leaking.
*/
static nsresult AddJSGCRoot(void* aPtr, const char* aName);
/**
* Remove aPtr as a JS GC root
*/
static nsresult RemoveJSGCRoot(jsval* aPtr) {
return RemoveJSGCRoot((void*)aPtr);
}
static nsresult RemoveJSGCRoot(JSObject** aPtr) {
return RemoveJSGCRoot((void*)aPtr);
}
static nsresult RemoveJSGCRoot(void* aPtr);
/**
* Quick helper to determine whether there are any mutation listeners
* of a given type that apply to this content or any of its ancestors.
@ -950,7 +916,7 @@ public:
PRBool aTryReuse);
/**
* Get the textual contents of a node. This is a concatination of all
* Get the textual contents of a node. This is a concatenation of all
* textnodes that are direct or (depending on aDeep) indirect children
* of the node.
*
@ -1000,40 +966,73 @@ public:
*/
static void DestroyAnonymousContent(nsCOMPtr<nsIContent>* aContent);
static nsresult HoldScriptObject(PRUint32 aLangID, void *aObject);
static nsresult DropScriptObject(PRUint32 aLangID, void *aObject);
class ScriptObjectHolder
/**
* Keep script object aNewObject, held by aScriptObjectHolder, alive.
*
* NOTE: This currently only supports objects that hold script objects of one
* scripting language.
*
* @param aLangID script language ID of aNewObject
* @param aScriptObjectHolder the object that holds aNewObject
* @param aTracer the tracer for aScriptObject
* @param aNewObject the script object to hold
* @param aWasHoldingObjects whether aScriptObjectHolder was already holding
* script objects (ie. HoldScriptObject was called
* on it before, without a corresponding call to
* DropScriptObjects)
*/
static nsresult HoldScriptObject(PRUint32 aLangID, void* aScriptObjectHolder,
nsScriptObjectTracer* aTracer,
void* aNewObject, PRBool aWasHoldingObjects)
{
public:
ScriptObjectHolder(PRUint32 aLangID) : mLangID(aLangID),
mObject(nsnull)
{
MOZ_COUNT_CTOR(ScriptObjectHolder);
if (aLangID == nsIProgrammingLanguage::JAVASCRIPT) {
return aWasHoldingObjects ? NS_OK :
HoldJSObjects(aScriptObjectHolder, aTracer);
}
~ScriptObjectHolder()
{
MOZ_COUNT_DTOR(ScriptObjectHolder);
if (mObject)
DropScriptObject(mLangID, mObject);
return HoldScriptObject(aLangID, aNewObject);
}
/**
* Drop any script objects that aScriptObjectHolder is holding.
*
* NOTE: This currently only supports objects that hold script objects of one
* scripting language.
*
* @param aLangID script language ID of the objects that
* @param aScriptObjectHolder the object that holds script object that we want
* to drop
* @param aTracer the tracer for aScriptObject
*/
static nsresult DropScriptObjects(PRUint32 aLangID, void* aScriptObjectHolder,
nsScriptObjectTracer* aTracer)
{
if (aLangID == nsIProgrammingLanguage::JAVASCRIPT) {
return DropJSObjects(aScriptObjectHolder);
}
nsresult set(void *aObject)
{
NS_ASSERTION(aObject, "unexpected null object");
NS_ASSERTION(!mObject, "already have an object");
nsresult rv = HoldScriptObject(mLangID, aObject);
if (NS_SUCCEEDED(rv)) {
mObject = aObject;
}
return rv;
}
void traverse(nsCycleCollectionTraversalCallback &cb)
{
cb.NoteScriptChild(mLangID, mObject);
}
PRUint32 mLangID;
void *mObject;
};
aTracer->Trace(aScriptObjectHolder, DropScriptObject, nsnull);
return NS_OK;
}
/**
* Keep the JS objects held by aScriptObjectHolder alive.
*
* @param aScriptObjectHolder the object that holds JS objects that we want to
* keep alive
* @param aTracer the tracer for aScriptObject
*/
static nsresult HoldJSObjects(void* aScriptObjectHolder,
nsScriptObjectTracer* aTracer);
/**
* Drop the JS objects held by aScriptObjectHolder.
*
* @param aScriptObjectHolder the object that holds JS objects that we want to
* drop
*/
static nsresult DropJSObjects(void* aScriptObjectHolder);
/**
* Convert nsIContent::IME_STATUS_* to nsIKBStateControll::IME_STATUS_*
@ -1120,6 +1119,10 @@ private:
static nsIDOMScriptObjectFactory *GetDOMScriptObjectFactory();
static nsresult HoldScriptObject(PRUint32 aLangID, void* aObject);
PR_STATIC_CALLBACK(void) DropScriptObject(PRUint32 aLangID, void *aObject,
void *aClosure);
static nsIDOMScriptObjectFactory *sDOMScriptObjectFactory;
static nsIXPConnect *sXPConnect;
@ -1161,14 +1164,9 @@ private:
// Holds pointers to nsISupports* that should be released at shutdown
static nsVoidArray* sPtrsToPtrsToRelease;
// For now, we don't want to automatically clean this up in Shutdown(), since
// consumers might unfortunately end up wanting to use it after that
static nsIJSRuntimeService* sJSRuntimeService;
static JSRuntime* sJSScriptRuntime;
static PRInt32 sJSScriptRootCount;
static nsIScriptRuntime* sScriptRuntimes[NS_STID_ARRAY_UBOUND];
static PRInt32 sScriptRootCount[NS_STID_ARRAY_UBOUND];
static PRUint32 sJSGCThingRootCount;
#ifdef IBMBIDI
static nsIBidiKeyboard* sBidiKeyboard;
@ -1178,6 +1176,14 @@ private:
};
#define NS_HOLD_JS_OBJECTS(obj, clazz) \
nsContentUtils::HoldJSObjects(NS_CYCLE_COLLECTION_UPCAST(obj, clazz), \
&NS_CYCLE_COLLECTION_NAME(clazz))
#define NS_DROP_JS_OBJECTS(obj, clazz) \
nsContentUtils::DropJSObjects(NS_CYCLE_COLLECTION_UPCAST(obj, clazz))
class nsCxPusher
{
public:
@ -1200,33 +1206,38 @@ public:
nsAutoGCRoot(jsval* aPtr, nsresult* aResult) :
mPtr(aPtr)
{
mResult = *aResult =
nsContentUtils::AddJSGCRoot(aPtr, "nsAutoGCRoot");
mResult = *aResult = AddJSGCRoot(aPtr, "nsAutoGCRoot");
}
// aPtr should be the pointer to the JSObject* we want to protect
nsAutoGCRoot(JSObject** aPtr, nsresult* aResult) :
mPtr(aPtr)
{
mResult = *aResult =
nsContentUtils::AddJSGCRoot(aPtr, "nsAutoGCRoot");
mResult = *aResult = AddJSGCRoot(aPtr, "nsAutoGCRoot");
}
// aPtr should be the pointer to the thing we want to protect
nsAutoGCRoot(void* aPtr, nsresult* aResult) :
mPtr(aPtr)
{
mResult = *aResult =
nsContentUtils::AddJSGCRoot(aPtr, "nsAutoGCRoot");
mResult = *aResult = AddJSGCRoot(aPtr, "nsAutoGCRoot");
}
~nsAutoGCRoot() {
if (NS_SUCCEEDED(mResult)) {
nsContentUtils::RemoveJSGCRoot(mPtr);
RemoveJSGCRoot(mPtr);
}
}
static void Shutdown();
private:
static nsresult AddJSGCRoot(void *aPtr, const char* aName);
static nsresult RemoveJSGCRoot(void *aPtr);
static nsIJSRuntimeService* sJSRuntimeService;
static JSRuntime* sJSScriptRuntime;
void* mPtr;
nsresult mResult;
};

Просмотреть файл

@ -100,8 +100,11 @@ enum {
NODE_IS_INSERTION_PARENT = 0x00001000U,
// Keep track of whether this node is in the middle of binding teardown
NODE_IS_IN_BINDING_TEARDOWN = 0x00002000U,
// Four bits for the script-type ID
NODE_SCRIPT_TYPE_OFFSET = 13,
NODE_SCRIPT_TYPE_OFFSET = 14,
NODE_SCRIPT_TYPE_SIZE = 4,

Просмотреть файл

@ -73,9 +73,9 @@ public:
* into AppendText calls.
*
* The current strategy is that we break the overall text into
* whitespace-delimited "words". Then for words that contain a "complex"
* character (currently CJK or Thai), we break within the word using complex
* rules (JISx4051 or Pango).
* whitespace-delimited "words". Then those words are passed to the nsILineBreaker
* service for deeper analysis if they contain a "complex" character as described
* below.
*/
class nsLineBreaker {
public:
@ -102,9 +102,9 @@ public:
(0xff00 <= u && u <= 0xffef); // Halfwidth and Fullwidth Forms
}
// Normally, break opportunities exist at the end of each run of whitespace
// (see IsSpace above). Break opportunities can also exist inside runs of
// non-whitespace, as determined by nsILineBreaker. We pass a whitespace-
// Break opportunities exist at the end of each run of breakable whitespace
// (see IsSpace above). Break opportunities can also exist between pairs of
// non-whitespace characters, as determined by nsILineBreaker. We pass a whitespace-
// delimited word to nsILineBreaker if it contains at least one character
// matching IsComplexChar.
// We provide flags to control on a per-chunk basis where breaks are allowed.
@ -114,22 +114,38 @@ public:
// We operate on text after whitespace processing has been applied, so
// other characters (e.g. tabs and newlines) may have been converted to
// spaces.
/**
* Flags passed with each chunk of text.
*/
enum {
/**
* Allow a break opportunity at the start of this chunk of text.
/*
* Do not introduce a break opportunity at the start of this chunk of text.
*/
BREAK_ALLOW_INITIAL = 0x01,
BREAK_SUPPRESS_INITIAL = 0x01,
/**
* Allow a break opportunity in the interior of this chunk of text.
* Do not introduce a break opportunity in the interior of this chunk of text.
* Also, whitespace in this chunk is treated as non-breakable.
*/
BREAK_ALLOW_INSIDE = 0x02
BREAK_SUPPRESS_INSIDE = 0x02,
/**
* The sink currently is already set up to have no breaks in it;
* if no breaks are possible, nsLineBreaker does not need to call
* SetBreaks on it. This is useful when handling large quantities of
* preformatted text; the textruns will never have any breaks set on them,
* and there is no need to ever actually scan the text for breaks, except
* at the end of textruns in case context is needed for following breakable
* text.
*/
BREAK_SKIP_SETTING_NO_BREAKS = 0x04
};
/**
* Append "invisible whitespace". This acts like whitespace, but there is
* no actual text associated with it.
* no actual text associated with it. Only the BREAK_SUPPRESS_INSIDE flag
* is relevant here.
*/
nsresult AppendInvisibleWhitespace();
nsresult AppendInvisibleWhitespace(PRUint32 aFlags);
/**
* Feed Unicode text into the linebreaker for analysis. aLength must be
@ -184,8 +200,11 @@ private:
nsAutoTArray<TextItem,2> mTextItems;
PRPackedBool mCurrentWordContainsComplexChar;
// True if the previous character was whitespace
PRPackedBool mAfterSpace;
// True if the previous character was breakable whitespace
PRPackedBool mAfterBreakableSpace;
// True if a break must be allowed at the current position because
// a run of breakable whitespace ends here
PRPackedBool mBreakHere;
};
#endif /*NSLINEBREAKER_H_*/

Просмотреть файл

@ -180,15 +180,15 @@ nsILineBreaker *nsContentUtils::sLineBreaker;
nsIWordBreaker *nsContentUtils::sWordBreaker;
nsICaseConversion *nsContentUtils::sCaseConv;
nsVoidArray *nsContentUtils::sPtrsToPtrsToRelease;
nsIJSRuntimeService *nsContentUtils::sJSRuntimeService;
JSRuntime *nsContentUtils::sJSScriptRuntime;
PRInt32 nsContentUtils::sJSScriptRootCount = 0;
nsIScriptRuntime *nsContentUtils::sScriptRuntimes[NS_STID_ARRAY_UBOUND];
PRInt32 nsContentUtils::sScriptRootCount[NS_STID_ARRAY_UBOUND];
PRUint32 nsContentUtils::sJSGCThingRootCount;
#ifdef IBMBIDI
nsIBidiKeyboard *nsContentUtils::sBidiKeyboard = nsnull;
#endif
nsIJSRuntimeService *nsAutoGCRoot::sJSRuntimeService;
JSRuntime *nsAutoGCRoot::sJSScriptRuntime;
PRBool nsContentUtils::sInitialized = PR_FALSE;
@ -671,7 +671,8 @@ nsContentUtils::Shutdown()
NS_IF_RELEASE(sStringBundleService);
NS_IF_RELEASE(sConsoleService);
NS_IF_RELEASE(sDOMScriptObjectFactory);
NS_IF_RELEASE(sXPConnect);
if (sJSGCThingRootCount == 0 && sXPConnect)
NS_RELEASE(sXPConnect);
NS_IF_RELEASE(sSecurityManager);
NS_IF_RELEASE(sThreadJSContextStack);
NS_IF_RELEASE(sNameSpaceManager);
@ -721,6 +722,8 @@ nsContentUtils::Shutdown()
sEventListenerManagersHash.ops = nsnull;
}
}
nsAutoGCRoot::Shutdown();
}
static PRBool IsCallerTrustedForCapability(const char* aCapability)
@ -2157,6 +2160,9 @@ nsContentUtils::LoadImage(nsIURI* aURI, nsIDocument* aLoadingDocument,
nsIURI *documentURI = aLoadingDocument->GetDocumentURI();
// Make the URI immutable so people won't change it under us
NS_TryToSetImmutable(aURI);
// We don't use aLoadingPrincipal for anything here yet... but we
// will. See bug 377092.
@ -2669,7 +2675,7 @@ nsContentUtils::GetContentPolicy()
// static
nsresult
nsContentUtils::AddJSGCRoot(void* aPtr, const char* aName)
nsAutoGCRoot::AddJSGCRoot(void* aPtr, const char* aName)
{
if (!sJSScriptRuntime) {
nsresult rv = CallGetService("@mozilla.org/js/xpc/RuntimeService;1",
@ -2687,25 +2693,16 @@ nsContentUtils::AddJSGCRoot(void* aPtr, const char* aName)
PRBool ok;
ok = ::JS_AddNamedRootRT(sJSScriptRuntime, aPtr, aName);
if (!ok) {
if (sJSScriptRootCount == 0) {
// We just got the runtime... Just null things out, since no
// one's expecting us to have a runtime yet
NS_RELEASE(sJSRuntimeService);
sJSScriptRuntime = nsnull;
}
NS_WARNING("JS_AddNamedRootRT failed");
return NS_ERROR_OUT_OF_MEMORY;
}
// We now have one more root we added to the runtime
++sJSScriptRootCount;
return NS_OK;
}
/* static */
nsresult
nsContentUtils::RemoveJSGCRoot(void* aPtr)
nsAutoGCRoot::RemoveJSGCRoot(void* aPtr)
{
if (!sJSScriptRuntime) {
NS_NOTREACHED("Trying to remove a JS GC root when none were added");
@ -2714,11 +2711,6 @@ nsContentUtils::RemoveJSGCRoot(void* aPtr)
::JS_RemoveRootRT(sJSScriptRuntime, aPtr);
if (--sJSScriptRootCount == 0) {
NS_RELEASE(sJSRuntimeService);
sJSScriptRuntime = nsnull;
}
return NS_OK;
}
@ -3522,6 +3514,8 @@ nsresult
nsContentUtils::HoldScriptObject(PRUint32 aLangID, void *aObject)
{
NS_ASSERTION(aObject, "unexpected null object");
NS_ASSERTION(aLangID != nsIProgrammingLanguage::JAVASCRIPT,
"Should use HoldJSObjects.");
nsresult rv;
PRUint32 langIndex = NS_STID_INDEX(aLangID);
@ -3548,17 +3542,47 @@ nsContentUtils::HoldScriptObject(PRUint32 aLangID, void *aObject)
}
/* static */
nsresult
nsContentUtils::DropScriptObject(PRUint32 aLangID, void *aObject)
void
nsContentUtils::DropScriptObject(PRUint32 aLangID, void *aObject,
void *aClosure)
{
NS_ASSERTION(aObject, "unexpected null object");
NS_ASSERTION(aLangID != nsIProgrammingLanguage::JAVASCRIPT,
"Should use DropJSObjects.");
PRUint32 langIndex = NS_STID_INDEX(aLangID);
NS_LOG_RELEASE(sScriptRuntimes[langIndex], sScriptRootCount[langIndex] - 1,
"HoldScriptObject");
nsresult rv = sScriptRuntimes[langIndex]->DropScriptObject(aObject);
sScriptRuntimes[langIndex]->DropScriptObject(aObject);
if (--sScriptRootCount[langIndex] == 0) {
NS_RELEASE(sScriptRuntimes[langIndex]);
}
}
/* static */
nsresult
nsContentUtils::HoldJSObjects(void* aScriptObjectHolder,
nsScriptObjectTracer* aTracer)
{
PRBool newHolder;
nsresult rv = sXPConnect->AddJSHolder(aScriptObjectHolder, aTracer);
NS_ENSURE_SUCCESS(rv, rv);
++sJSGCThingRootCount;
NS_LOG_ADDREF(sXPConnect, sJSGCThingRootCount, "HoldJSObjects",
sizeof(void*));
return NS_OK;
}
/* static */
nsresult
nsContentUtils::DropJSObjects(void* aScriptObjectHolder)
{
NS_LOG_RELEASE(sXPConnect, sJSGCThingRootCount - 1, "HoldJSObjects");
nsresult rv = sXPConnect->RemoveJSHolder(aScriptObjectHolder);
if (--sJSGCThingRootCount == 0 && !sInitialized) {
NS_RELEASE(sXPConnect);
}
return rv;
}
@ -3640,7 +3664,7 @@ nsContentUtils::CheckSecurityBeforeLoad(nsIURI* aURIToLoad,
nsCOMPtr<nsIURI> loadingURI;
rv = aLoadingPrincipal->GetURI(getter_AddRefs(loadingURI));
NS_ENSURE_SUCCESS(rv, rv);
return sSecurityManager->CheckSameOriginURI(loadingURI, aURIToLoad);
return sSecurityManager->CheckSameOriginURI(loadingURI, aURIToLoad, PR_TRUE);
}
/* static */
@ -3698,10 +3722,26 @@ nsContentUtils::IsNativeAnonymous(nsIContent* aContent)
return PR_TRUE;
}
NS_ASSERTION(!aContent->IsNativeAnonymous(),
// Nasty hack to work around spell-check resolving style on
// native-anonymous content that's already been torn down. Don't assert
// !IsNativeAnonymous() if aContent->GetCurrentDoc() is null. The caller
// will get "wrong" style data, but it's just asking for that sort of thing
// anyway.
NS_ASSERTION(!aContent->IsNativeAnonymous() ||
!aContent->GetCurrentDoc() ||
(aContent->GetParent() &&
aContent->GetParent()->NodeInfo()->
Equals(nsGkAtoms::use, kNameSpaceID_SVG)),
"Native anonymous node with wrong binding parent");
aContent = bindingParent;
}
return PR_FALSE;
}
/* static */
void
nsAutoGCRoot::Shutdown()
{
NS_IF_RELEASE(sJSRuntimeService);
}

Просмотреть файл

@ -134,7 +134,7 @@ nsCrossSiteListenerProxy::OnStartRequest(nsIRequest* aRequest,
nsCOMPtr<nsIURI> finalURI;
channel->GetURI(getter_AddRefs(finalURI));
rv = nsContentUtils::GetSecurityManager()->
CheckSameOriginURI(mRequestingURI, finalURI);
CheckSameOriginURI(mRequestingURI, finalURI, PR_FALSE);
if (NS_SUCCEEDED(rv)) {
mAcceptState = eAccept;
return ForwardRequest(PR_FALSE);

Просмотреть файл

@ -1161,13 +1161,7 @@ nsDocument::Reset(nsIChannel* aChannel, nsILoadGroup* aLoadGroup)
// Note: this code is duplicated in nsXULDocument::StartDocumentLoad and
// nsScriptSecurityManager::GetChannelPrincipal.
// Note: this should match nsDocShell::OnLoadingSite
nsLoadFlags loadFlags = 0;
nsresult rv = aChannel->GetLoadFlags(&loadFlags);
if (NS_SUCCEEDED(rv) && (loadFlags & nsIChannel::LOAD_REPLACE)) {
aChannel->GetURI(getter_AddRefs(uri));
} else {
aChannel->GetOriginalURI(getter_AddRefs(uri));
}
NS_GetFinalChannelURI(aChannel, getter_AddRefs(uri));
nsIScriptSecurityManager *securityManager =
nsContentUtils::GetSecurityManager();

Просмотреть файл

@ -792,6 +792,9 @@ protected:
nsString mBaseTarget;
// Our update nesting level
PRUint32 mUpdateNestLevel;
private:
friend class nsUnblockOnloadEvent;
@ -833,9 +836,6 @@ private:
// Member to store out last-selected stylesheet set.
nsString mLastStyleSheetSet;
// Our update nesting level
PRUint32 mUpdateNestLevel;
};

Просмотреть файл

@ -838,6 +838,7 @@ GK_ATOM(thead, "thead")
GK_ATOM(thumb, "thumb")
GK_ATOM(title, "title")
GK_ATOM(titlebar, "titlebar")
GK_ATOM(titlebarcolor, "titlebarcolor")
GK_ATOM(titletip, "titletip")
GK_ATOM(toggled, "toggled")
GK_ATOM(token, "token")

Просмотреть файл

@ -42,7 +42,7 @@
nsLineBreaker::nsLineBreaker()
: mCurrentWordContainsComplexChar(PR_FALSE),
mAfterSpace(PR_FALSE)
mAfterBreakableSpace(PR_FALSE), mBreakHere(PR_FALSE)
{
}
@ -72,10 +72,10 @@ nsLineBreaker::FlushCurrentWord()
TextItem* ti = &mTextItems[i];
NS_ASSERTION(ti->mLength > 0, "Zero length word contribution?");
if (!(ti->mFlags & BREAK_ALLOW_INITIAL) && ti->mSinkOffset == 0) {
if ((ti->mFlags & BREAK_SUPPRESS_INITIAL) && ti->mSinkOffset == 0) {
breakState[offset] = PR_FALSE;
}
if (!(ti->mFlags & BREAK_ALLOW_INSIDE)) {
if (ti->mFlags & BREAK_SUPPRESS_INSIDE) {
PRUint32 exclude = ti->mSinkOffset == 0 ? 1 : 0;
memset(breakState.Elements() + offset + exclude, PR_FALSE, ti->mLength - exclude);
}
@ -107,7 +107,7 @@ nsLineBreaker::AppendText(nsIAtom* aLangGroup, const PRUnichar* aText, PRUint32
// Continue the current word
if (mCurrentWord.Length() > 0) {
NS_ASSERTION(!mAfterSpace, "These should not be set");
NS_ASSERTION(!mAfterBreakableSpace && !mBreakHere, "These should not be set");
while (offset < aLength && !IsSpace(aText[offset])) {
mCurrentWord.AppendElement(aText[offset]);
@ -137,8 +137,14 @@ nsLineBreaker::AppendText(nsIAtom* aLangGroup, const PRUnichar* aText, PRUint32
}
PRUint32 start = offset;
if (!aSink && !aFlags) {
// Skip to the space before the last word, since we don't need the breaks
PRBool noBreaksNeeded = !aSink ||
((aFlags & BREAK_SUPPRESS_INITIAL) && (aFlags & BREAK_SUPPRESS_INSIDE) &&
!mBreakHere && !mAfterBreakableSpace && (aFlags & BREAK_SKIP_SETTING_NO_BREAKS));
if (noBreaksNeeded) {
// Skip to the space before the last word, since either the break data
// here is not needed, or no breaks are set in the sink and there cannot
// be any breaks in this chunk; all we need is the context for the next
// chunk (if any)
offset = aLength;
while (offset > start) {
--offset;
@ -152,16 +158,17 @@ nsLineBreaker::AppendText(nsIAtom* aLangGroup, const PRUnichar* aText, PRUint32
for (;;) {
PRUnichar ch = aText[offset];
PRBool isSpace = IsSpace(ch);
PRBool isBreakableSpace = isSpace && !(aFlags & BREAK_SUPPRESS_INSIDE);
if (aSink) {
breakState[offset] = mAfterSpace && !isSpace &&
(aFlags & (offset == 0 ? BREAK_ALLOW_INITIAL : BREAK_ALLOW_INSIDE));
breakState[offset] = mBreakHere || (mAfterBreakableSpace && !isBreakableSpace);
}
mAfterSpace = isSpace;
mBreakHere = PR_FALSE;
mAfterBreakableSpace = isBreakableSpace;
if (isSpace) {
if (offset > wordStart && wordHasComplexChar) {
if (aSink && (aFlags & BREAK_ALLOW_INSIDE)) {
if (aSink && !(aFlags & BREAK_SUPPRESS_INSIDE)) {
// Save current start-of-word state because GetJISx4051Breaks will
// set it to false
PRPackedBool currentStart = breakState[wordStart];
@ -198,7 +205,7 @@ nsLineBreaker::AppendText(nsIAtom* aLangGroup, const PRUnichar* aText, PRUint32
}
}
if (aSink) {
if (!noBreaksNeeded) {
aSink->SetBreaks(start, offset - start, breakState.Elements() + start);
}
return NS_OK;
@ -214,7 +221,7 @@ nsLineBreaker::AppendText(nsIAtom* aLangGroup, const PRUint8* aText, PRUint32 aL
// Continue the current word
if (mCurrentWord.Length() > 0) {
NS_ASSERTION(!mAfterSpace, "These should not be set");
NS_ASSERTION(!mAfterBreakableSpace && !mBreakHere, "These should not be set");
while (offset < aLength && !IsSpace(aText[offset])) {
mCurrentWord.AppendElement(aText[offset]);
@ -247,8 +254,14 @@ nsLineBreaker::AppendText(nsIAtom* aLangGroup, const PRUint8* aText, PRUint32 aL
}
PRUint32 start = offset;
if (!aSink && !aFlags) {
// Skip to the space before the last word, since we don't need the breaks
PRBool noBreaksNeeded = !aSink ||
((aFlags & BREAK_SUPPRESS_INITIAL) && (aFlags & BREAK_SUPPRESS_INSIDE) &&
!mBreakHere && !mAfterBreakableSpace && (aFlags & BREAK_SKIP_SETTING_NO_BREAKS));
if (noBreaksNeeded) {
// Skip to the space before the last word, since either the break data
// here is not needed, or no breaks are set in the sink and there cannot
// be any breaks in this chunk; all we need is the context for the next
// chunk (if any)
offset = aLength;
while (offset > start) {
--offset;
@ -262,16 +275,17 @@ nsLineBreaker::AppendText(nsIAtom* aLangGroup, const PRUint8* aText, PRUint32 aL
for (;;) {
PRUint8 ch = aText[offset];
PRBool isSpace = IsSpace(ch);
PRBool isBreakableSpace = isSpace && !(aFlags & BREAK_SUPPRESS_INSIDE);
if (aSink) {
breakState[offset] = mAfterSpace && !isSpace &&
(aFlags & (offset == 0 ? BREAK_ALLOW_INITIAL : BREAK_ALLOW_INSIDE));
breakState[offset] = mBreakHere || (mAfterBreakableSpace && !isBreakableSpace);
}
mAfterSpace = isSpace;
mBreakHere = PR_FALSE;
mAfterBreakableSpace = isBreakableSpace;
if (isSpace) {
if (offset > wordStart && wordHasComplexChar) {
if (aSink && (aFlags & BREAK_ALLOW_INSIDE)) {
if (aSink && !(aFlags & BREAK_SUPPRESS_INSIDE)) {
// Save current start-of-word state because GetJISx4051Breaks will
// set it to false
PRPackedBool currentStart = breakState[wordStart];
@ -311,18 +325,22 @@ nsLineBreaker::AppendText(nsIAtom* aLangGroup, const PRUint8* aText, PRUint32 aL
}
}
if (aSink) {
if (!noBreaksNeeded) {
aSink->SetBreaks(start, offset - start, breakState.Elements() + start);
}
return NS_OK;
}
nsresult
nsLineBreaker::AppendInvisibleWhitespace() {
// Treat as "invisible whitespace"
nsLineBreaker::AppendInvisibleWhitespace(PRUint32 aFlags) {
nsresult rv = FlushCurrentWord();
if (NS_FAILED(rv))
return rv;
mAfterSpace = PR_TRUE;
PRBool isBreakableSpace = !(aFlags & BREAK_SUPPRESS_INSIDE);
if (mAfterBreakableSpace && !isBreakableSpace) {
mBreakHere = PR_TRUE;
}
mAfterBreakableSpace = isBreakableSpace;
return NS_OK;
}

Просмотреть файл

@ -194,7 +194,7 @@ nsSyncLoader::LoadDocument(nsIChannel* aChannel,
nsIScriptSecurityManager::STANDARD);
NS_ENSURE_SUCCESS(rv, rv);
rv = securityManager->CheckSameOriginURI(aLoaderURI, docURI);
rv = securityManager->CheckSameOriginURI(aLoaderURI, docURI, PR_TRUE);
NS_ENSURE_SUCCESS(rv, rv);
}
@ -378,7 +378,7 @@ nsSyncLoader::OnChannelRedirect(nsIChannel *aOldChannel,
nsIScriptSecurityManager *securityManager =
nsContentUtils::GetSecurityManager();
rv = securityManager->CheckSameOriginURI(oldURI, newURI);
rv = securityManager->CheckSameOriginURI(oldURI, newURI, PR_TRUE);
NS_ENSURE_SUCCESS(rv, rv);
mChannel = aNewChannel;

Просмотреть файл

@ -56,6 +56,7 @@
#include "prprf.h"
#include "nsIDOMEventListener.h"
#include "nsIJSContextStack.h"
#include "nsJSEnvironment.h"
#include "nsIScriptSecurityManager.h"
#include "nsWeakPtr.h"
#include "nsICharsetAlias.h"
@ -1149,7 +1150,8 @@ IsSameOrigin(nsIPrincipal* aPrincipal, nsIChannel* aChannel)
rv = aChannel->GetURI(getter_AddRefs(channelURI));
NS_ENSURE_SUCCESS(rv, rv);
rv = nsContentUtils::GetSecurityManager()->CheckSameOriginURI(codebase, channelURI);
rv = nsContentUtils::GetSecurityManager()->
CheckSameOriginURI(codebase, channelURI, PR_FALSE);
return NS_SUCCEEDED(rv);
}
@ -1778,6 +1780,7 @@ nsXMLHttpRequest::RequestCompleted()
ChangeState(XML_HTTP_REQUEST_OPENED);
}
nsJSContext::MaybeCC(PR_FALSE);
return rv;
}
@ -2320,6 +2323,7 @@ nsXMLHttpRequest::Error(nsIDOMEvent* aEvent)
NotifyEventListeners(errorEventListeners, event);
}
nsJSContext::MaybeCC(PR_FALSE);
return NS_OK;
}

Просмотреть файл

@ -2465,6 +2465,13 @@ nsCanvasRenderingContext2D::GetImageData()
PRUint8 g = *row++;
PRUint8 b = *row++;
#endif
// Convert to non-premultiplied color
if (a != 0) {
r = (r * 255) / a;
g = (g * 255) / a;
b = (b * 255) / a;
}
*dest++ = INT_TO_JSVAL(r);
*dest++ = INT_TO_JSVAL(g);
*dest++ = INT_TO_JSVAL(b);
@ -2588,6 +2595,11 @@ nsCanvasRenderingContext2D::PutImageData()
else if (JSVAL_IS_DOUBLE(va)) ia = (PRUint8) (*JSVAL_TO_DOUBLE(va));
else return NS_ERROR_DOM_SYNTAX_ERR;
// Convert to premultiplied color (losslessly if the input came from getImageData)
ir = (ir*ia + 254) / 255;
ig = (ig*ia + 254) / 255;
ib = (ib*ia + 254) / 255;
#ifdef IS_LITTLE_ENDIAN
*imgPtr++ = ib;
*imgPtr++ = ig;

Просмотреть файл

@ -136,6 +136,9 @@
#include "nsEventDispatcher.h"
#include "nsPresShellIterator.h"
#include "nsServiceManagerUtils.h"
#include "nsITimer.h"
#ifdef XP_MACOSX
#include <Events.h>
#endif
@ -144,6 +147,8 @@
//#define DEBUG_DOCSHELL_FOCUS
#endif
#define NS_USER_INTERACTION_INTERVAL 5000 // ms
static NS_DEFINE_CID(kFrameTraversalCID, NS_FRAMETRAVERSAL_CID);
@ -171,12 +176,48 @@ static PRUint32 sESMInstanceCount = 0;
static PRInt32 sChromeAccessModifier = 0, sContentAccessModifier = 0;
PRInt32 nsEventStateManager::sUserInputEventDepth = 0;
static PRUint32 gMouseOrKeyboardEventCounter = 0;
static nsITimer* gUserInteractionTimer = nsnull;
static nsITimerCallback* gUserInteractionTimerCallback = nsnull;
class nsUITimerCallback : public nsITimerCallback
{
public:
nsUITimerCallback() : mPreviousCount(0) {}
NS_DECL_ISUPPORTS
NS_DECL_NSITIMERCALLBACK
private:
PRUint32 mPreviousCount;
};
NS_IMPL_ISUPPORTS1(nsUITimerCallback, nsITimerCallback)
// If aTimer is nsnull, this method always sends "user-interaction-inactive"
// notification.
NS_IMETHODIMP
nsUITimerCallback::Notify(nsITimer* aTimer)
{
nsresult rv;
nsCOMPtr<nsIObserverService> obs =
do_GetService("@mozilla.org/observer-service;1", &rv);
NS_ENSURE_SUCCESS(rv, rv);
if ((gMouseOrKeyboardEventCounter == mPreviousCount) || !aTimer) {
gMouseOrKeyboardEventCounter = 0;
obs->NotifyObservers(nsnull, "user-interaction-inactive", nsnull);
} else {
obs->NotifyObservers(nsnull, "user-interaction-active", nsnull);
}
mPreviousCount = gMouseOrKeyboardEventCounter;
return NS_OK;
}
enum {
MOUSE_SCROLL_N_LINES,
MOUSE_SCROLL_PAGE,
MOUSE_SCROLL_HISTORY,
MOUSE_SCROLL_TEXTSIZE,
MOUSE_SCROLL_PIXELS
MOUSE_SCROLL_PIXELS,
MOUSE_SCROLL_FULLZOOM
};
struct AccessKeyInfo {
@ -431,6 +472,18 @@ nsEventStateManager::nsEventStateManager()
mTabbedThroughDocument(PR_FALSE),
mAccessKeys(nsnull)
{
if (sESMInstanceCount == 0) {
gUserInteractionTimerCallback = new nsUITimerCallback();
if (gUserInteractionTimerCallback) {
NS_ADDREF(gUserInteractionTimerCallback);
CallCreateInstance("@mozilla.org/timer;1", &gUserInteractionTimer);
if (gUserInteractionTimer) {
gUserInteractionTimer->InitWithCallback(gUserInteractionTimerCallback,
NS_USER_INTERACTION_INTERVAL,
nsITimer::TYPE_REPEATING_SLACK);
}
}
}
++sESMInstanceCount;
}
@ -509,6 +562,14 @@ nsEventStateManager::~nsEventStateManager()
if(sESMInstanceCount == 0) {
NS_IF_RELEASE(gLastFocusedContent);
NS_IF_RELEASE(gLastFocusedDocument);
if (gUserInteractionTimerCallback) {
gUserInteractionTimerCallback->Notify(nsnull);
NS_RELEASE(gUserInteractionTimerCallback);
}
if (gUserInteractionTimer) {
gUserInteractionTimer->Cancel();
NS_RELEASE(gUserInteractionTimer);
}
}
delete mAccessKeys;
@ -724,6 +785,25 @@ nsEventStateManager::PreHandleEvent(nsPresContext* aPresContext,
if (!mCurrentTarget) return NS_ERROR_NULL_POINTER;
}
// Do not take account NS_MOUSE_ENTER/EXIT so that loading a page
// when user is not active doesn't change the state to active.
if (NS_IS_TRUSTED_EVENT(aEvent) &&
((aEvent->eventStructType == NS_MOUSE_EVENT &&
static_cast<nsMouseEvent*>(aEvent)->reason == nsMouseEvent::eReal &&
aEvent->message != NS_MOUSE_ENTER &&
aEvent->message != NS_MOUSE_EXIT) ||
aEvent->eventStructType == NS_MOUSE_SCROLL_EVENT ||
aEvent->eventStructType == NS_KEY_EVENT)) {
if (gMouseOrKeyboardEventCounter == 0) {
nsCOMPtr<nsIObserverService> obs =
do_GetService("@mozilla.org/observer-service;1");
if (obs) {
obs->NotifyObservers(nsnull, "user-interaction-active", nsnull);
}
}
++gMouseOrKeyboardEventCounter;
}
*aStatus = nsEventStatus_eIgnore;
nsMouseWheelTransaction::OnEvent(aEvent);
@ -1859,8 +1939,10 @@ nsEventStateManager::GenerateDragGesture(nsPresContext* aPresContext,
} // GenerateDragGesture
nsresult
nsEventStateManager::ChangeTextSize(PRInt32 change)
nsEventStateManager::GetMarkupDocumentViewer(nsIMarkupDocumentViewer** aMv)
{
*aMv = nsnull;
if(!gLastFocusedDocument) return NS_ERROR_FAILURE;
nsPIDOMWindow* ourWindow = gLastFocusedDocument->GetWindow();
@ -1894,6 +1976,19 @@ nsEventStateManager::ChangeTextSize(PRInt32 change)
nsCOMPtr<nsIMarkupDocumentViewer> mv(do_QueryInterface(cv));
if(!mv) return NS_ERROR_FAILURE;
*aMv = mv;
NS_IF_ADDREF(*aMv);
return NS_OK;
}
nsresult
nsEventStateManager::ChangeTextSize(PRInt32 change)
{
nsCOMPtr<nsIMarkupDocumentViewer> mv;
nsresult rv = GetMarkupDocumentViewer(getter_AddRefs(mv));
NS_ENSURE_SUCCESS(rv, rv);
float textzoom;
mv->GetTextZoom(&textzoom);
textzoom += ((float)change) / 10;
@ -1903,6 +1998,27 @@ nsEventStateManager::ChangeTextSize(PRInt32 change)
return NS_OK;
}
nsresult
nsEventStateManager::ChangeFullZoom(PRInt32 change)
{
nsCOMPtr<nsIMarkupDocumentViewer> mv;
nsresult rv = GetMarkupDocumentViewer(getter_AddRefs(mv));
NS_ENSURE_SUCCESS(rv, rv);
float fullzoom;
float zoomMin = ((float)nsContentUtils::GetIntPref("fullZoom.minPercent", 50)) / 100;
float zoomMax = ((float)nsContentUtils::GetIntPref("fullZoom.maxPercent", 300)) / 100;
mv->GetFullZoom(&fullzoom);
fullzoom += ((float)change) / 10;
if (fullzoom < zoomMin)
fullzoom = zoomMin;
else if (fullzoom > zoomMax)
fullzoom = zoomMax;
mv->SetFullZoom(fullzoom);
return NS_OK;
}
void
nsEventStateManager::DoScrollHistory(PRInt32 direction)
{
@ -1934,6 +2050,21 @@ nsEventStateManager::DoScrollTextsize(nsIFrame *aTargetFrame,
}
}
void
nsEventStateManager::DoScrollFullZoom(nsIFrame *aTargetFrame,
PRInt32 adjustment)
{
// Exclude form controls and XUL content.
nsIContent *content = aTargetFrame->GetContent();
if (content &&
!content->IsNodeOfType(nsINode::eHTML_FORM_CONTROL) &&
!content->IsNodeOfType(nsINode::eXUL))
{
// negative adjustment to increase zoom, positive to decrease
ChangeFullZoom((adjustment > 0) ? -1 : 1);
}
}
static nsIFrame*
GetParentFrameToScroll(nsPresContext* aPresContext, nsIFrame* aFrame)
{
@ -2317,6 +2448,12 @@ nsEventStateManager::PostHandleEvent(nsPresContext* aPresContext,
}
break;
case MOUSE_SCROLL_FULLZOOM:
{
DoScrollFullZoom(aTargetFrame, msEvent->delta);
}
break;
default: // Including -1 (do nothing)
break;
}

Просмотреть файл

@ -51,6 +51,7 @@
#include "nsCOMArray.h"
#include "nsIFrame.h"
#include "nsCycleCollectionParticipant.h"
#include "nsIMarkupDocumentViewer.h"
class nsIScrollableView;
class nsIPresShell;
@ -304,7 +305,10 @@ protected:
void ForceViewUpdate(nsIView* aView);
void DoScrollHistory(PRInt32 direction);
void DoScrollTextsize(nsIFrame *aTargetFrame, PRInt32 adjustment);
void DoScrollFullZoom(nsIFrame *aTargetFrame, PRInt32 adjustment);
nsresult GetMarkupDocumentViewer(nsIMarkupDocumentViewer** aMv);
nsresult ChangeTextSize(PRInt32 change);
nsresult ChangeFullZoom(PRInt32 change);
// end mousewheel functions
// routines for the d&d gesture tracking state machine

Просмотреть файл

@ -764,16 +764,10 @@ nsFSMultipartFormData::AddNameValuePair(nsIDOMHTMLElement* aSource,
// XXX: name parameter should be encoded per RFC 2231
// RFC 2388 specifies that RFC 2047 be used, but I think it's not
// consistent with MIME standard.
// NOTE: The ordering of these headers, and in particular which comes first
// and which comes last, is important. See comments in
// nsFSMultipartFormData::AddNameFilePair
mPostDataChunk += NS_LITERAL_CSTRING("--") + mBoundary
+ NS_LITERAL_CSTRING(CRLF)
+ NS_LITERAL_CSTRING("Content-Disposition: form-data; name=\"")
+ nameStr + NS_LITERAL_CSTRING("\"" CRLF)
+ NS_LITERAL_CSTRING("Content-Type: text/plain; charset=")
+ mCharset
+ NS_LITERAL_CSTRING(CRLF CRLF)
+ nameStr + NS_LITERAL_CSTRING("\"" CRLF CRLF)
+ valueStr + NS_LITERAL_CSTRING(CRLF);
return NS_OK;
@ -800,23 +794,12 @@ nsFSMultipartFormData::AddNameFilePair(nsIDOMHTMLElement* aSource,
+ NS_LITERAL_CSTRING(CRLF);
if (!mBackwardsCompatibleSubmit) {
// XXX Is there any way to tell when "8bit" or "7bit" etc may be
// XXXbz See bug 58189 for why we try to send it and bug 83065 for why we
// don't just always do it. It seems like a better solution would be to
// just make sure we send this header before the Content-Type header (to
// deal with the PHP brain-deadness described in bug 83065), but to send it
// anyway. However, we need to make sure it comes after the
// Content-Disposition header, because other server-side packages make the
// equally brain-dead assumption that Content-Disposition is the first
// header in every part. See bug 116346 for that fun.
mPostDataChunk +=
NS_LITERAL_CSTRING("Content-Transfer-Encoding: binary" CRLF);
}
// XXX: name/filename parameter should be encoded per RFC 2231
// RFC 2388 specifies that RFC 2047 be used, but I think it's not
// consistent with the MIME standard.
// NOTE: The Content-Disposition MUST come first and the Content-Type last to
// satisfy non-MIME-compliant server-side parsers. See comment above on
// Content-Transfer-Encoding.
mPostDataChunk +=
NS_LITERAL_CSTRING("Content-Disposition: form-data; name=\"")
+ nameStr + NS_LITERAL_CSTRING("\"; filename=\"")
@ -1160,9 +1143,6 @@ GetSubmissionFromForm(nsGenericHTMLElement* aForm,
nsCOMPtr<nsISaveAsCharset> encoder;
nsFormSubmission::GetEncoder(aForm, charset, getter_AddRefs(encoder));
if (!encoder)
charset.AssignLiteral("UTF-8");
// Get form processor
nsCOMPtr<nsIFormProcessor> formProcessor =
do_GetService(kFormProcessorCID, &rv);

Просмотреть файл

@ -1703,30 +1703,21 @@ nsHTMLDocument::SetDomain(const nsAString& aDomain)
nsAutoString current;
if (NS_FAILED(GetDomain(current)))
return NS_ERROR_FAILURE;
PRBool ok = PR_FALSE;
if (current.Equals(aDomain)) {
ok = PR_TRUE;
} else if (aDomain.Length() < current.Length()) {
nsAutoString suffix;
current.Right(suffix, aDomain.Length());
PRUnichar c = current.CharAt(current.Length() - aDomain.Length() - 1);
if (suffix.Equals(aDomain, nsCaseInsensitiveStringComparator()) &&
(c == '.')) {
// Using only a TLD is forbidden (bug 368700)
nsCOMPtr<nsIEffectiveTLDService> tldService =
do_GetService(NS_EFFECTIVETLDSERVICE_CONTRACTID);
if (!tldService)
return NS_ERROR_NOT_AVAILABLE;
PRBool ok = current.Equals(aDomain);
if (current.Length() > aDomain.Length() &&
StringEndsWith(current, aDomain, nsCaseInsensitiveStringComparator()) &&
current.CharAt(current.Length() - aDomain.Length() - 1) == '.') {
// Using only a TLD is forbidden (bug 368700)
nsCOMPtr<nsIEffectiveTLDService> tldService =
do_GetService(NS_EFFECTIVETLDSERVICE_CONTRACTID);
if (!tldService)
return NS_ERROR_NOT_AVAILABLE;
NS_ConvertUTF16toUTF8 str(aDomain);
PRUint32 tldLength;
nsresult rv = tldService->GetEffectiveTLDLength(str, &tldLength);
if (NS_FAILED(rv))
return rv;
if (tldLength < str.Length())
ok = PR_TRUE;
}
// try to get the base domain; if this works, we're ok
NS_ConvertUTF16toUTF8 str(aDomain);
nsCAutoString etld;
nsresult rv = tldService->GetBaseDomainFromHost(str, 0, etld);
ok = NS_SUCCEEDED(rv);
}
if (!ok) {
// Error: illegal domain
@ -2219,6 +2210,7 @@ nsHTMLDocument::OpenCommon(const nsACString& aContentType, PRBool aReplace)
if (root) {
// Tear down the frames for the root element.
MOZ_AUTO_DOC_UPDATE(this, UPDATE_CONTENT_MODEL, PR_TRUE);
nsNodeUtils::ContentRemoved(this, root, 0);
// Put the root element back into the document, we don't notify
@ -3740,6 +3732,16 @@ nsHTMLDocument::GetDesignMode(nsAString & aDesignMode)
return NS_OK;
}
void
nsHTMLDocument::EndUpdate(nsUpdateType aUpdateType)
{
nsDocument::EndUpdate(aUpdateType);
if (mUpdateNestLevel == 0 && mContentEditableCount > 0 != IsEditingOn()) {
EditingStateChanged();
}
}
nsresult
nsHTMLDocument::ChangeContentEditableCount(nsIContent *aElement,
PRInt32 aChange)
@ -3749,7 +3751,8 @@ nsHTMLDocument::ChangeContentEditableCount(nsIContent *aElement,
mContentEditableCount += aChange;
if (mParser) {
if (mParser ||
(mUpdateNestLevel > 0 && mContentEditableCount > 0 != IsEditingOn())) {
return NS_OK;
}

Просмотреть файл

@ -212,6 +212,8 @@ public:
mDisableCookieAccess = PR_TRUE;
}
void EndUpdate(nsUpdateType aUpdateType);
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED_NO_UNLINK(nsHTMLDocument, nsDocument)
protected:

Просмотреть файл

@ -184,28 +184,22 @@ GetValueFromString(const nsAString &aValueAsString,
float *aValue,
PRUint16 *aUnitType)
{
char *str = ToNewCString(aValueAsString);
if (!str)
return NS_ERROR_OUT_OF_MEMORY;
NS_ConvertUTF16toUTF8 value(aValueAsString);
const char *str = value.get();
nsresult rv = NS_ERROR_FAILURE;
if (NS_IsAsciiWhitespace(*str))
return NS_ERROR_FAILURE;
if (*str) {
char *rest;
*aValue = static_cast<float>(PR_strtod(str, &rest));
if (rest != str) {
*aUnitType = GetUnitTypeForString(nsCRT::strtok(rest,
"\x20\x9\xD\xA",
&rest));
if (IsValidUnitType(*aUnitType)) {
rv = NS_OK;
}
char *rest;
*aValue = float(PR_strtod(str, &rest));
if (rest != str) {
*aUnitType = GetUnitTypeForString(rest);
if (IsValidUnitType(*aUnitType)) {
return NS_OK;
}
}
nsMemory::Free(str);
return rv;
return NS_ERROR_FAILURE;
}
float

Просмотреть файл

@ -52,12 +52,18 @@ nsSVGInteger::SetBaseValueString(const nsAString &aValueAsString,
nsSVGElement *aSVGElement,
PRBool aDoSetAttr)
{
nsAutoString s;
s.Assign(aValueAsString);
PRInt32 err;
PRInt32 val = s.ToInteger(&err);
nsresult rv = static_cast<nsresult>(err);
NS_ENSURE_SUCCESS(rv, rv);
NS_ConvertUTF16toUTF8 value(aValueAsString);
const char *str = value.get();
if (NS_IsAsciiWhitespace(*str))
return NS_ERROR_FAILURE;
char *rest;
PRInt32 val = strtol(str, &rest, 10);
if (rest == str || *rest != '\0') {
return NS_ERROR_FAILURE;
}
mBaseVal = mAnimVal = val;
return NS_OK;
}

Просмотреть файл

@ -145,28 +145,22 @@ GetValueFromString(const nsAString &aValueAsString,
float *aValue,
PRUint16 *aUnitType)
{
char *str = ToNewCString(aValueAsString);
if (!str)
return NS_ERROR_OUT_OF_MEMORY;
NS_ConvertUTF16toUTF8 value(aValueAsString);
const char *str = value.get();
nsresult rv = NS_ERROR_FAILURE;
if (NS_IsAsciiWhitespace(*str))
return NS_ERROR_FAILURE;
if (*str) {
char *rest;
*aValue = static_cast<float>(PR_strtod(str, &rest));
if (rest != str) {
*aUnitType = GetUnitTypeForString(nsCRT::strtok(rest,
"\x20\x9\xD\xA",
&rest));
if (IsValidUnitType(*aUnitType)) {
rv = NS_OK;
}
char *rest;
*aValue = float(PR_strtod(str, &rest));
if (rest != str) {
*aUnitType = GetUnitTypeForString(rest);
if (IsValidUnitType(*aUnitType)) {
return NS_OK;
}
}
nsMemory::Free(str);
return rv;
return NS_ERROR_FAILURE;
}
float

Просмотреть файл

@ -54,12 +54,18 @@ nsSVGNumber2::SetBaseValueString(const nsAString &aValueAsString,
nsSVGElement *aSVGElement,
PRBool aDoSetAttr)
{
nsAutoString s;
s.Assign(aValueAsString);
PRInt32 err;
float val = s.ToFloat(&err);
nsresult rv = static_cast<nsresult>(err);
NS_ENSURE_SUCCESS(rv, rv);
NS_ConvertUTF16toUTF8 value(aValueAsString);
const char *str = value.get();
if (NS_IsAsciiWhitespace(*str))
return NS_ERROR_FAILURE;
char *rest;
float val = float(PR_strtod(str, &rest));
if (rest == str || *rest != '\0') {
return NS_ERROR_FAILURE;
}
mBaseVal = mAnimVal = val;
return NS_OK;
}

Просмотреть файл

@ -915,7 +915,10 @@ nsBindingManager::DoProcessAttachedQueue()
mProcessAttachedQueueEvent = nsnull;
if (mDocument) {
mDocument->UnblockOnload(PR_TRUE);
// Hold a strong reference while calling UnblockOnload since that might
// run script.
nsCOMPtr<nsIDocument> doc = mDocument;
doc->UnblockOnload(PR_TRUE);
}
}
@ -933,6 +936,11 @@ nsBindingManager::ProcessAttachedQueue()
mAttachedStack.RemoveElementAt(lastItem);
NS_ASSERTION(binding, "null item in attached stack?");
nsresult rv = binding->EnsureScriptAPI();
if (NS_FAILED(rv)) {
return;
}
binding->ExecuteAttachedHandler();
}

Просмотреть файл

@ -186,6 +186,11 @@ XBLResolve(JSContext *cx, JSObject *obj, jsval id, uintN flags,
return JS_FALSE;
}
if (content->HasFlag(NODE_IS_IN_BINDING_TEARDOWN)) {
// Don't evaluate fields now!
return JS_TRUE;
}
// This mirrors code in nsXBLProtoImpl::InstallImplementation
nsIDocument* doc = content->GetOwnerDoc();
if (!doc) {
@ -272,7 +277,8 @@ nsXBLBinding::nsXBLBinding(nsXBLPrototypeBinding* aBinding)
: mPrototypeBinding(aBinding),
mInsertionPointTable(nsnull),
mIsStyleBinding(PR_TRUE),
mMarkedForDeath(PR_FALSE)
mMarkedForDeath(PR_FALSE),
mInstalledAPI(PR_FALSE)
{
NS_ASSERTION(mPrototypeBinding, "Must have a prototype binding!");
// Grab a ref to the document info so the prototype binding won't die
@ -300,7 +306,7 @@ TraverseKey(nsISupports* aKey, nsInsertionPointList* aData, void* aClosure)
return PL_DHASH_NEXT;
}
NS_IMPL_CYCLE_COLLECTION_NATIVE_CLASS(nsXBLBinding)
NS_IMPL_CYCLE_COLLECTION_CLASS(nsXBLBinding)
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_NATIVE(nsXBLBinding)
// XXX Probably can't unlink mPrototypeBinding->XBLDocumentInfo(), because
// mPrototypeBinding is weak.
@ -375,18 +381,6 @@ nsXBLBinding::SetBoundElement(nsIContent* aElement)
mNextBinding->SetBoundElement(aElement);
}
nsXBLBinding*
nsXBLBinding::GetFirstBindingWithConstructor()
{
if (mPrototypeBinding->GetConstructor())
return this;
if (mNextBinding)
return mNextBinding->GetFirstBindingWithConstructor();
return nsnull;
}
PRBool
nsXBLBinding::HasStyleSheets() const
{
@ -800,6 +794,22 @@ nsXBLBinding::GenerateAnonymousContent()
}
}
nsresult
nsXBLBinding::EnsureScriptAPI()
{
if (mInstalledAPI) {
return NS_OK;
}
// Set mInstalledAPI right away since we'll recurse into here from
// nsElementSH::PostCreate when InstallImplementation is called.
mInstalledAPI = PR_TRUE;
InstallEventHandlers();
return InstallImplementation();
}
void
nsXBLBinding::InstallEventHandlers()
{
@ -1039,25 +1049,19 @@ void
nsXBLBinding::ChangeDocument(nsIDocument* aOldDocument, nsIDocument* aNewDocument)
{
if (aOldDocument != aNewDocument) {
if (mNextBinding)
mNextBinding->ChangeDocument(aOldDocument, aNewDocument);
// Only style bindings get their prototypes unhooked.
// Only style bindings get their prototypes unhooked. First do ourselves.
if (mIsStyleBinding) {
// Now the binding dies. Unhook our prototypes.
nsIContent* interfaceElement =
mPrototypeBinding->GetImmediateChild(nsGkAtoms::implementation);
if (interfaceElement) {
nsIScriptGlobalObject *global = aOldDocument->GetScriptGlobalObject();
if (mPrototypeBinding->HasImplementation()) {
nsIScriptGlobalObject *global = aOldDocument->GetScopeObject();
if (global) {
nsIScriptContext *context = global->GetContext();
nsCOMPtr<nsIScriptContext> context = global->GetContext();
if (context) {
JSContext *jscontext = (JSContext *)context->GetNativeContext();
JSContext *cx = (JSContext *)context->GetNativeContext();
nsCOMPtr<nsIXPConnectJSObjectHolder> wrapper;
nsresult rv = nsContentUtils::XPConnect()->
WrapNative(jscontext, global->GetGlobalJSObject(),
WrapNative(cx, global->GetGlobalJSObject(),
mBoundElement, NS_GET_IID(nsISupports),
getter_AddRefs(wrapper));
if (NS_FAILED(rv))
@ -1070,16 +1074,62 @@ nsXBLBinding::ChangeDocument(nsIDocument* aOldDocument, nsIDocument* aNewDocumen
// XXX Stay in sync! What if a layered binding has an
// <interface>?!
// XXXbz what does that comment mean, really? It seems to date
// back to when there was such a thing as an <interface>, whever
// that was...
// XXX Sanity check to make sure our class name matches
// Pull ourselves out of the proto chain.
JSObject* ourProto = ::JS_GetPrototype(jscontext, scriptObject);
if (ourProto)
{
JSObject* grandProto = ::JS_GetPrototype(jscontext, ourProto);
::JS_SetPrototype(jscontext, scriptObject, grandProto);
// Find the right prototype.
JSObject* base = scriptObject;
JSObject* proto;
JSAutoRequest ar(cx);
for ( ; true; base = proto) { // Will break out on null proto
proto = ::JS_GetPrototype(cx, base);
if (!proto) {
break;
}
JSClass* clazz = ::JS_GetClass(cx, proto);
if (!clazz ||
(~clazz->flags &
(JSCLASS_HAS_PRIVATE | JSCLASS_PRIVATE_IS_NSISUPPORTS)) ||
JSCLASS_RESERVED_SLOTS(clazz) != 1) {
// Clearly not the right class
continue;
}
nsCOMPtr<nsIXBLDocumentInfo> docInfo =
do_QueryInterface(static_cast<nsISupports*>
(::JS_GetPrivate(cx, proto)));
if (!docInfo) {
// Not the proto we seek
continue;
}
jsval protoBinding;
if (!::JS_GetReservedSlot(cx, proto, 0, &protoBinding)) {
NS_ERROR("Really shouldn't happen");
continue;
}
if (JSVAL_TO_PRIVATE(protoBinding) != mPrototypeBinding) {
// Not the right binding
continue;
}
// Alright! This is the right prototype. Pull it out of the
// proto chain.
JSObject* grandProto = ::JS_GetPrototype(cx, proto);
::JS_SetPrototype(cx, base, grandProto);
break;
}
// Do this after unhooking the proto to avoid extra walking along
// the proto chain as the JS engine tries to resolve the properties
// we're removing.
mBoundElement->SetFlags(NODE_IS_IN_BINDING_TEARDOWN);
mPrototypeBinding->UndefineFields(cx, scriptObject);
mBoundElement->UnsetFlags(NODE_IS_IN_BINDING_TEARDOWN);
// Don't remove the reference from the document to the
// wrapper here since it'll be removed by the element
// itself when that's taken out of the document.
@ -1088,7 +1138,14 @@ nsXBLBinding::ChangeDocument(nsIDocument* aOldDocument, nsIDocument* aNewDocumen
}
}
// Then do our ancestors. This reverses the construction order, so that at
// all times things are consistent as far as everyone is concerned.
if (mNextBinding) {
mNextBinding->ChangeDocument(aOldDocument, aNewDocument);
}
// Update the anonymous content.
// XXXbz why not only for style bindings?
nsIContent *anonymous = mContent;
if (anonymous) {
// Also kill the default content within all our insertion points.

Просмотреть файл

@ -120,15 +120,13 @@ public:
void GenerateAnonymousContent();
void InstallAnonymousContent(nsIContent* aAnonParent, nsIContent* aElement);
void InstallEventHandlers();
nsresult InstallImplementation();
nsresult EnsureScriptAPI();
void ExecuteAttachedHandler();
void ExecuteDetachedHandler();
void UnhookEventHandlers();
nsIAtom* GetBaseTag(PRInt32* aNameSpaceID);
nsXBLBinding* GetFirstBindingWithConstructor();
nsXBLBinding* RootBinding();
nsXBLBinding* GetFirstStyleBinding();
@ -169,6 +167,12 @@ public:
// MEMBER VARIABLES
protected:
// These two functions recursively install the event handlers
// and implementation on this binding and its base class bindings.
// External callers should call EnsureScriptAPI instead.
void InstallEventHandlers();
nsresult InstallImplementation();
nsAutoRefCnt mRefCnt;
nsXBLPrototypeBinding* mPrototypeBinding; // Weak, but we're holding a ref to the docinfo
nsCOMPtr<nsIContent> mContent; // Strong. Our anonymous content stays around with us.
@ -181,6 +185,7 @@ protected:
PRPackedBool mIsStyleBinding;
PRPackedBool mMarkedForDeath;
PRPackedBool mInstalledAPI;
};
#endif // nsXBLBinding_h_

Просмотреть файл

@ -452,6 +452,21 @@ UnlinkProtos(nsHashKey *aKey, void *aData, void* aClosure)
return kHashEnumerateNext;
}
struct ProtoTracer
{
TraceCallback mCallback;
void *mClosure;
};
static PRIntn PR_CALLBACK
TraceProtos(nsHashKey *aKey, void *aData, void* aClosure)
{
ProtoTracer* closure = static_cast<ProtoTracer*>(aClosure);
nsXBLPrototypeBinding *proto = static_cast<nsXBLPrototypeBinding*>(aData);
proto->Trace(closure->mCallback, closure->mClosure);
return kHashEnumerateNext;
}
NS_IMPL_CYCLE_COLLECTION_CLASS(nsXBLDocumentInfo)
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN(nsXBLDocumentInfo)
if (tmp->mBindingTable) {
@ -466,7 +481,14 @@ NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN(nsXBLDocumentInfo)
tmp->mBindingTable->Enumerate(TraverseProtos, &cb);
}
cb.NoteXPCOMChild(static_cast<nsIScriptGlobalObject*>(tmp->mGlobalObject));
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_SCRIPT_OBJECTS
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
NS_IMPL_CYCLE_COLLECTION_TRACE_BEGIN(nsXBLDocumentInfo)
if (tmp->mBindingTable) {
ProtoTracer closure = { aCallback, aClosure };
tmp->mBindingTable->Enumerate(TraceProtos, &closure);
}
NS_IMPL_CYCLE_COLLECTION_TRACE_END
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(nsXBLDocumentInfo)
NS_INTERFACE_MAP_ENTRY(nsIXBLDocumentInfo)
@ -507,7 +529,10 @@ nsXBLDocumentInfo::~nsXBLDocumentInfo()
mGlobalObject->SetScriptContext(nsIProgrammingLanguage::JAVASCRIPT, nsnull);
mGlobalObject->ClearGlobalObjectOwner(); // just in case
}
delete mBindingTable;
if (mBindingTable) {
NS_DROP_JS_OBJECTS(this, nsXBLDocumentInfo);
delete mBindingTable;
}
}
NS_IMETHODIMP
@ -541,8 +566,13 @@ DeletePrototypeBinding(nsHashKey* aKey, void* aData, void* aClosure)
NS_IMETHODIMP
nsXBLDocumentInfo::SetPrototypeBinding(const nsACString& aRef, nsXBLPrototypeBinding* aBinding)
{
if (!mBindingTable)
if (!mBindingTable) {
mBindingTable = new nsObjectHashtable(nsnull, nsnull, DeletePrototypeBinding, nsnull);
if (!mBindingTable)
return NS_ERROR_OUT_OF_MEMORY;
NS_HOLD_JS_OBJECTS(this, nsXBLDocumentInfo);
}
const nsPromiseFlatCString& flat = PromiseFlatCString(aRef);
nsCStringKey key(flat.get());

Просмотреть файл

@ -72,8 +72,8 @@ public:
// nsIScriptGlobalObjectOwner methods
virtual nsIScriptGlobalObject* GetScriptGlobalObject();
NS_DECL_CYCLE_COLLECTION_CLASS_AMBIGUOUS(nsXBLDocumentInfo,
nsIXBLDocumentInfo)
NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS_AMBIGUOUS(nsXBLDocumentInfo,
nsIXBLDocumentInfo)
private:
nsCOMPtr<nsIDocument> mDocument;

Просмотреть файл

@ -64,7 +64,7 @@ nsXBLInsertionPoint::Release()
return mRefCnt;
}
NS_IMPL_CYCLE_COLLECTION_NATIVE_CLASS(nsXBLInsertionPoint)
NS_IMPL_CYCLE_COLLECTION_CLASS(nsXBLInsertionPoint)
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN_NATIVE(nsXBLInsertionPoint)
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMARRAY(mElements)
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mDefaultContentTemplate)

Просмотреть файл

@ -200,7 +200,7 @@ nsXBLProtoImpl::CompilePrototypeMembers(nsXBLPrototypeBinding* aBinding)
}
void
nsXBLProtoImpl::Traverse(nsCycleCollectionTraversalCallback &cb) const
nsXBLProtoImpl::Trace(TraceCallback aCallback, void *aClosure) const
{
// If we don't have a class object then we either didn't compile members
// or we only have fields, in both cases there are no cycles through our
@ -211,7 +211,7 @@ nsXBLProtoImpl::Traverse(nsCycleCollectionTraversalCallback &cb) const
nsXBLProtoImplMember *member;
for (member = mMembers; member; member = member->GetNext()) {
member->Traverse(cb);
member->Trace(aCallback, aClosure);
}
}
@ -254,6 +254,19 @@ nsXBLProtoImpl::ResolveAllFields(JSContext *cx, JSObject *obj) const
return PR_TRUE;
}
void
nsXBLProtoImpl::UndefineFields(JSContext *cx, JSObject *obj) const
{
JSAutoRequest ar(cx);
for (nsXBLProtoImplField* f = mFields; f; f = f->GetNext()) {
nsDependentString name(f->GetName());
jsval dummy;
::JS_DeleteUCProperty2(cx, obj,
reinterpret_cast<const jschar*>(name.get()),
name.Length(), &dummy);
}
}
void
nsXBLProtoImpl::DestroyMembers(nsXBLProtoImplMember* aBrokenMember)
{

Просмотреть файл

@ -90,7 +90,7 @@ public:
mFields = aFieldList;
}
void Traverse(nsCycleCollectionTraversalCallback &cb) const;
void Trace(TraceCallback aCallback, void *aClosure) const;
void Unlink();
nsXBLProtoImplField* FindField(const nsString& aFieldName) const;
@ -99,6 +99,10 @@ public:
// return means a JS exception was set.
PRBool ResolveAllFields(JSContext *cx, JSObject *obj) const;
// Undefine all our fields from object |obj| (which should be a
// JSObject for a bound element).
void UndefineFields(JSContext* cx, JSObject* obj) const;
PRBool CompiledMembers() const {
return mClassObject != nsnull;
}

Просмотреть файл

@ -47,11 +47,11 @@
#include "nsIJSRuntimeService.h"
#include "nsIServiceManager.h"
#include "nsReadableUtils.h"
#include "nsCycleCollectionParticipant.h"
class nsIScriptContext;
struct JSRuntime;
class nsIJSRuntimeService;
class nsCycleCollectionTraversalCallback;
struct nsXBLTextWithLineNumber
{
@ -114,7 +114,7 @@ public:
const nsCString& aClassStr,
void* aClassObject)=0;
virtual void Traverse(nsCycleCollectionTraversalCallback &cb) const = 0;
virtual void Trace(TraceCallback aCallback, void *aClosure) const = 0;
protected:
friend class nsAutoGCRoot;

Просмотреть файл

@ -72,8 +72,6 @@ nsXBLProtoImplMethod::Destroy(PRBool aIsCompiled)
NS_PRECONDITION(aIsCompiled == mIsCompiled,
"Incorrect aIsCompiled in nsXBLProtoImplMethod::Destroy");
if (aIsCompiled) {
if (mJSMethodObject)
nsContentUtils::RemoveJSGCRoot(&mJSMethodObject);
mJSMethodObject = nsnull;
}
else {
@ -263,8 +261,6 @@ nsXBLProtoImplMethod::CompileMember(nsIScriptContext* aContext, const nsCString&
if (methodObject) {
// Root the compiled prototype script object.
rv = nsContentUtils::AddJSGCRoot(&mJSMethodObject,
"nsXBLProtoImplMethod::mJSMethodObject");
if (NS_FAILED(rv)) {
mJSMethodObject = nsnull;
}
@ -277,11 +273,13 @@ nsXBLProtoImplMethod::CompileMember(nsIScriptContext* aContext, const nsCString&
}
void
nsXBLProtoImplMethod::Traverse(nsCycleCollectionTraversalCallback &cb) const
nsXBLProtoImplMethod::Trace(TraceCallback aCallback, void *aClosure) const
{
NS_ASSERTION(mIsCompiled, "Shouldn't traverse uncompiled method");
cb.NoteScriptChild(nsIProgrammingLanguage::JAVASCRIPT, mJSMethodObject);
if (mJSMethodObject) {
aCallback(nsIProgrammingLanguage::JAVASCRIPT, mJSMethodObject, aClosure);
}
}
nsresult

Просмотреть файл

@ -129,7 +129,7 @@ public:
const nsCString& aClassStr,
void* aClassObject);
virtual void Traverse(nsCycleCollectionTraversalCallback &cb) const;
virtual void Trace(TraceCallback aCallback, void *aClosure) const;
protected:
union {

Просмотреть файл

@ -87,14 +87,14 @@ nsXBLProtoImplProperty::Destroy(PRBool aIsCompiled)
"Incorrect aIsCompiled in nsXBLProtoImplProperty::Destroy");
if ((mJSAttributes & JSPROP_GETTER) && mJSGetterObject) {
nsContentUtils::RemoveJSGCRoot(&mJSGetterObject);
mJSGetterObject = nsnull;
}
else {
delete mGetterText;
}
if ((mJSAttributes & JSPROP_SETTER) && mJSSetterObject) {
nsContentUtils::RemoveJSGCRoot(&mJSSetterObject);
mJSSetterObject = nsnull;
}
else {
delete mSetterText;
@ -268,9 +268,6 @@ nsXBLProtoImplProperty::CompileMember(nsIScriptContext* aContext, const nsCStrin
if (mJSGetterObject && NS_SUCCEEDED(rv)) {
mJSAttributes |= JSPROP_GETTER | JSPROP_SHARED;
// Root the compiled prototype script object.
rv = nsContentUtils::AddJSGCRoot(&mJSGetterObject,
"nsXBLProtoImplProperty::mJSGetterObject");
}
if (NS_FAILED(rv)) {
mJSGetterObject = nsnull;
@ -320,9 +317,6 @@ nsXBLProtoImplProperty::CompileMember(nsIScriptContext* aContext, const nsCStrin
if (mJSSetterObject && NS_SUCCEEDED(rv)) {
mJSAttributes |= JSPROP_SETTER | JSPROP_SHARED;
// Root the compiled prototype script object.
rv = nsContentUtils::AddJSGCRoot(&mJSSetterObject,
"nsXBLProtoImplProperty::mJSSetterObject");
}
if (NS_FAILED(rv)) {
mJSSetterObject = nsnull;
@ -345,15 +339,15 @@ nsXBLProtoImplProperty::CompileMember(nsIScriptContext* aContext, const nsCStrin
}
void
nsXBLProtoImplProperty::Traverse(nsCycleCollectionTraversalCallback &cb) const
nsXBLProtoImplProperty::Trace(TraceCallback aCallback, void *aClosure) const
{
NS_ASSERTION(mIsCompiled, "Shouldn't traverse uncompiled method");
if (mJSAttributes & JSPROP_GETTER) {
cb.NoteScriptChild(nsIProgrammingLanguage::JAVASCRIPT, mJSGetterObject);
if ((mJSAttributes & JSPROP_GETTER) && mJSGetterObject) {
aCallback(nsIProgrammingLanguage::JAVASCRIPT, mJSGetterObject, aClosure);
}
if (mJSAttributes & JSPROP_SETTER) {
cb.NoteScriptChild(nsIProgrammingLanguage::JAVASCRIPT, mJSSetterObject);
if ((mJSAttributes & JSPROP_SETTER) && mJSSetterObject) {
aCallback(nsIProgrammingLanguage::JAVASCRIPT, mJSSetterObject, aClosure);
}
}

Просмотреть файл

@ -72,7 +72,7 @@ public:
const nsCString& aClassStr,
void* aClassObject);
virtual void Traverse(nsCycleCollectionTraversalCallback &cb) const;
virtual void Trace(TraceCallback aCallback, void *aClosure) const;
protected:
union {

Некоторые файлы не были показаны из-за слишком большого количества измененных файлов Показать больше