RetroZilla/browser/components/places/content/bookmarkProperties.js
2015-10-20 23:03:22 -04:00

871 lines
28 KiB
JavaScript

//* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* ***** 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 the Places Bookmark Properties.
*
* The Initial Developer of the Original Code is Google Inc.
* Portions created by the Initial Developer are Copyright (C) 2006
* the Initial Developer. All Rights Reserved.
*
* Contributor(s):
* Joe Hughes <jhughes@google.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 GPL or the LGPL. 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 ***** */
#include controller.js
#include ../../../../toolkit/content/debug.js
var BookmarkPropertiesPanel = {
/** UI Text Strings */
__strings: null,
get _strings() {
if (!this.__strings) {
this.__strings = document.getElementById("stringBundle");
}
return this.__strings;
},
/**
* The Bookmarks Service.
*/
__bms: null,
get _bms() {
if (!this.__bms) {
this.__bms =
Cc["@mozilla.org/browser/nav-bookmarks-service;1"].
getService(Ci.nsINavBookmarksService);
}
return this.__bms;
},
/**
* The Nav History Service.
*/
__hist: null,
get _hist() {
if (!this.__hist) {
this.__hist =
Cc["@mozilla.org/browser/nav-history-service;1"].
getService(Ci.nsINavHistoryService);
}
return this.__hist;
},
/**
* The I/O Service, useful for creating nsIURIs from strings.
*/
__ios: null,
get _ios() {
if (!this.__ios) {
this.__ios =
Cc["@mozilla.org/network/io-service;1"].
getService(Ci.nsIIOService);
}
return this.__ios;
},
/**
* The Live Bookmark service for dealing with syndication feed folders.
*/
__livemarks: null,
get _livemarks() {
if (!this.__livemarks) {
this.__livemarks =
Cc["@mozilla.org/browser/livemark-service;1"].
getService(Ci.nsILivemarkService);
}
return this.__livemarks;
},
/**
* The Microsummary Service for displaying microsummaries.
*/
__mss: null,
get _mss() {
if (!this.__mss)
this.__mss = Cc["@mozilla.org/microsummary/service;1"].
getService(Ci.nsIMicrosummaryService);
return this.__mss;
},
_bookmarkURI: null,
_bookmarkTitle: "",
_microsummaries: null,
_dialogWindow: null,
_parentWindow: null,
_controller: null,
EDIT_BOOKMARK_VARIANT: 0,
ADD_BOOKMARK_VARIANT: 1,
EDIT_FOLDER_VARIANT: 2,
ADD_MULTIPLE_BOOKMARKS_VARIANT: 3,
ADD_LIVEMARK_VARIANT: 4,
EDIT_LIVEMARK_VARIANT: 5,
/**
* The variant identifier for the current instance of the dialog.
* The possibilities are enumerated by the constants above.
*/
_variant: null,
_isVariant: function BPP__isVariant(variant) {
return this._variant == variant;
},
/**
* Returns true if this variant of the dialog uses a URI as a primary
* identifier for the item being edited.
*/
_identifierIsURI: function BPP__identifierIsURI() {
switch(this._variant) {
case this.EDIT_FOLDER_VARIANT:
case this.ADD_MULTIPLE_BOOKMARKS_VARIANT:
case this.ADD_LIVEMARK_VARIANT:
case this.EDIT_LIVEMARK_VARIANT:
return false;
default:
return true;
}
},
/**
* Returns true if this variant of the dialog uses a folder ID as a primary
* identifier for the item being edited.
*/
_identifierIsFolderID: function BPP__identifierIsFolderID() {
switch(this._variant) {
case this.EDIT_FOLDER_VARIANT:
case this.EDIT_LIVEMARK_VARIANT:
return true;
default:
return false;
}
},
/**
* Returns true if the URI is editable in this variant of the dialog.
*/
_isURIEditable: function BPP__isURIEditable() {
switch(this._variant) {
case this.EDIT_FOLDER_VARIANT:
case this.ADD_MULTIPLE_BOOKMARKS_VARIANT:
case this.EDIT_LIVEMARK_VARIANT:
case this.ADD_LIVEMARK_VARIANT:
return false;
default:
return true;
}
},
/**
* Returns true if the shortcut field is visible in this
* variant of the dialog.
*/
_isShortcutVisible: function BPP__isShortcutVisible() {
switch(this._variant) {
case this.EDIT_FOLDER_VARIANT:
case this.ADD_MULTIPLE_BOOKMARKS_VARIANT:
case this.ADD_LIVEMARK_VARIANT:
case this.EDIT_LIVEMARK_VARIANT:
return false;
default:
return true;
}
},
/**
* Returns true if the livemark feed and site URI fields are visible.
*/
_areLivemarkURIsVisible: function BPP__areLivemarkURIsVisible() {
switch(this._variant) {
case this.ADD_LIVEMARK_VARIANT:
case this.EDIT_LIVEMARK_VARIANT:
return true;
default:
return false;
}
},
/**
* Returns true if the microsummary field is visible in this variant
* of the dialog.
*/
_isMicrosummaryVisible: function BPP__isMicrosummaryVisible() {
switch(this._variant) {
case this.EDIT_FOLDER_VARIANT:
case this.ADD_MULTIPLE_BOOKMARKS_VARIANT:
case this.ADD_LIVEMARK_VARIANT:
case this.EDIT_LIVEMARK_VARIANT:
return false;
default:
return true;
}
},
/**
* Returns true if bookmark deletion is possible from the current
* variant of the dialog.
*/
_isDeletePossible: function BPP__isDeletePossible() {
switch(this._variant) {
case this.ADD_BOOKMARK_VARIANT:
case this.ADD_MULTIPLE_BOOKMARKS_VARIANT:
case this.EDIT_FOLDER_VARIANT:
return false;
default:
return true;
}
},
/**
* Returns true if the URI's folder is editable in this variant
* of the dialog.
*/
_isFolderEditable: function BPP__isFolderEditable() {
switch(this._variant) {
case this.ADD_BOOKMARK_VARIANT:
case this.ADD_MULTIPLE_BOOKMARKS_VARIANT:
return true;
default:
return false;
}
},
/**
* This method returns the correct label for the dialog's "accept"
* button based on the variant of the dialog.
*/
_getAcceptLabel: function BPP__getAcceptLabel() {
switch(this._variant) {
case this.ADD_BOOKMARK_VARIANT:
case this.ADD_LIVEMARK_VARIANT:
return this._strings.getString("dialogAcceptLabelAdd");
case this.ADD_MULTIPLE_BOOKMARKS_VARIANT:
return this._strings.getString("dialogAcceptLabelAddMulti");
default:
return this._strings.getString("dialogAcceptLabelEdit");
}
},
/**
* This method returns the correct title for the current variant
* of this dialog.
*/
_getDialogTitle: function BPP__getDialogTitle() {
switch(this._variant) {
case this.ADD_BOOKMARK_VARIANT:
return this._strings.getString("dialogTitleAdd");
case this.EDIT_FOLDER_VARIANT:
return this._strings.getString("dialogTitleFolderEdit");
case this.ADD_MULTIPLE_BOOKMARKS_VARIANT:
return this._strings.getString("dialogTitleAddMulti");
case this.ADD_LIVEMARK_VARIANT:
return this._strings.getString("dialogTitleAddLivemark");
default:
return this._strings.getString("dialogTitleBookmarkEdit");
}
},
/**
* Returns a string representing the folder tree selection type for
* the given dialog variant. This is either "single" when you can only
* select one folder (usually because we're dealing with the location
* of a child folder, which can only have one parent), or "multiple"
* when you can select multiple folders (bookmarks can be in multiple
* folders).
*/
_getFolderSelectionType: function BPP__getFolderSelectionType() {
switch(this._variant) {
case this.ADD_MULTIPLE_BOOKMARKS_VARIANT:
case this.EDIT_FOLDER_VARIANT:
case this.EDIT_LIVEMARK_VARIANT:
return "single";
default:
return "multiple";
}
},
/**
* This method can be run on a URI parameter to ensure that it didn't
* receive a string instead of an nsIURI object.
*/
_assertURINotString: function BPP__assertURINotString(value) {
NS_ASSERT((typeof(value) == "object") && !(value instanceof String),
"This method should be passed a URI as a nsIURI object, not as a string.");
},
/**
* Determines the correct variant of the dialog to display depending
* on which action is passed in and the properties of the identifier value
* (generally either a URI or a folder ID).
*
* NOTE: It's currently not possible to create the dialog with a folder
* id and "add" mode.
*
* @param identifier the URI or folder ID to display the properties for
* @param action -- "add" if this is being triggered from an "add bookmark"
* UI action; or "edit" if this is being triggered from
* a "properties" UI action; or "addmulti" if we're
* trying to create multiple bookmarks
*
* @returns one of the *_VARIANT constants
*/
_determineVariant: function BPP__determineVariant(identifier, action) {
if (action == "add") {
this._assertURINotString(identifier);
if (this._bms.isBookmarked(identifier)) {
return this.EDIT_BOOKMARK_VARIANT;
}
else {
return this.ADD_BOOKMARK_VARIANT;
}
}
else if (action == "addmulti") {
return this.ADD_MULTIPLE_BOOKMARKS_VARIANT;
}
else { /* Assume "edit" */
if (typeof(identifier) == "number") {
if (this._livemarks.isLivemark(identifier)) {
return this.EDIT_LIVEMARK_VARIANT;
}
else {
return this.EDIT_FOLDER_VARIANT;
}
}
NS_ASSERT(this._bms.isBookmarked(identifier),
"Bookmark Properties dialog instantiated with " +
"non-bookmarked URI: \"" + identifier + "\"");
return this.EDIT_BOOKMARK_VARIANT;
}
},
/**
* This method returns the title string corresponding to a given URI.
* If none is available from the bookmark service (probably because
* the given URI doesn't appear in bookmarks or history), we synthesize
* a title from the first 100 characters of the URI.
*
* @param uri a nsIURI object for which we want the title
*
* @returns a title string
*/
_getURITitle: function BPP__getURITitle(uri) {
this._assertURINotString(uri);
var title = this._bms.getItemTitle(uri);
/* If we can't get a title for a new bookmark, let's set it to
be the first 100 characters of the URI. */
if (title == null) {
title = uri.spec;
if (title.length > 100) {
title = title.substr(0, 100);
}
}
return title;
},
/**
* This method should be called by the onload of the Bookmark Properties
* dialog to initialize the state of the panel.
*
* @param identifier a nsIURI object representing the bookmarked URI or
* integer folder ID of the item that
* we want to view the properties of
* @param dialogWindow the window object of the Bookmark Properties dialog
* @param controller a PlacesController object for interacting with the
* Places system
*/
init: function BPP_init(dialogWindow, identifier, controller, action) {
this._variant = this._determineVariant(identifier, action);
if (this._identifierIsURI()) {
this._assertURINotString(identifier);
this._bookmarkURI = identifier;
}
else if (this._identifierIsFolderID()){
this._folderId = identifier;
}
else if (this._isVariant(this.ADD_MULTIPLE_BOOKMARKS_VARIANT)) {
this._URIList = identifier;
}
this._dialogWindow = dialogWindow;
this._controller = controller;
this._initFolderTree();
this._populateProperties();
this._updateSize();
},
/**
* This method initializes the folder tree.
*/
_initFolderTree: function BPP__initFolderTree() {
this._folderTree = this._dialogWindow.document.getElementById("folderTree");
this._folderTree.peerDropTypes = [];
this._folderTree.childDropTypes = [];
this._folderTree.excludeItems = true;
this._folderTree.setAttribute("seltype", this._getFolderSelectionType());
var query = this._hist.getNewQuery();
query.setFolders([this._bms.placesRoot], 1);
var options = this._hist.getNewQueryOptions();
options.setGroupingMode([Ci.nsINavHistoryQueryOptions.GROUP_BY_FOLDER], 1);
options.excludeReadOnlyFolders = true;
options.excludeQueries = true;
this._folderTree.load([query], options);
},
/**
* This is a shorter form of getElementById for the dialog document.
* Given a XUL element ID from the dialog, returns the corresponding
* DOM element.
*
* @param XUL element ID
* @returns corresponding DOM element, or null if none found
*/
_element: function BPP__element(id) {
return this._dialogWindow.document.getElementById(id);
},
/**
* Hides the XUL element with the given ID.
*
* @param string ID of the XUL element to hide
*/
_hide: function BPP__hide(id) {
this._element(id).setAttribute("hidden", "true");
},
/**
* This method fills in the data values for the fields in the dialog.
*/
_populateProperties: function BPP__populateProperties() {
var document = this._dialogWindow.document;
if (this._identifierIsURI()) {
this._bookmarkTitle = this._getURITitle(this._bookmarkURI);
}
else if (this._identifierIsFolderID()){
this._bookmarkTitle = this._bms.getFolderTitle(this._folderId);
}
this._dialogWindow.document.title = this._getDialogTitle();
this._dialogWindow.document.documentElement.getButton("accept").label =
this._getAcceptLabel();
if (!this._isDeletePossible()) {
this._dialogWindow.document.documentElement.getButton("extra1").hidden =
"true";
}
var nurl = this._element("editURLBar");
var titlebox = this._element("editTitleBox");
titlebox.value = this._bookmarkTitle;
if (this._isURIEditable()) {
nurl.value = this._bookmarkURI.spec;
}
else {
this._hide("locationRow");
}
if (this._areLivemarkURIsVisible()) {
if (this._identifierIsFolderID()) {
var feedURI = this._livemarks.getFeedURI(this._folderId);
if (feedURI)
this._element("editLivemarkFeedLocationBox").value = feedURI.spec;
var siteURI = this._livemarks.getSiteURI(this._folderId);
if (siteURI)
this._element("editLivemarkSiteLocationBox").value = siteURI.spec;
}
} else {
this._hide("livemarkFeedLocationRow");
this._hide("livemarkSiteLocationRow");
}
if (this._isShortcutVisible()) {
var shortcutbox = this._element("editShortcutBox");
shortcutbox.value = this._bms.getKeywordForURI(this._bookmarkURI);
}
else {
this._hide("shortcutRow");
}
if (this._isMicrosummaryVisible()) {
this._microsummaries = this._mss.getMicrosummaries(this._bookmarkURI,
this._bookmarkURI);
this._microsummaries.addObserver(this._microsummaryObserver);
this._rebuildMicrosummaryPicker();
}
else {
var microsummaryRow =
this._dialogWindow.document.getElementById("microsummaryRow");
microsummaryRow.setAttribute("hidden", "true");
}
if (this._isFolderEditable()) {
this._folderTree.selectFolders([this._bms.bookmarksRoot]);
}
else {
this._hide("folderRow");
}
},
_rebuildMicrosummaryPicker: function BPP__rebuildMicrosummaryPicker() {
var microsummaryMenuList = document.getElementById("microsummaryMenuList");
var microsummaryMenuPopup = document.getElementById("microsummaryMenuPopup");
// Remove old items from the menu, except the first item, which represents
// "don't show a microsummary; show the page title instead".
while (microsummaryMenuPopup.childNodes.length > 1)
microsummaryMenuPopup.removeChild(microsummaryMenuPopup.lastChild);
var enumerator = this._microsummaries.Enumerate();
while (enumerator.hasMoreElements()) {
var microsummary = enumerator.getNext().QueryInterface(Ci.nsIMicrosummary);
var menuItem = document.createElement("menuitem");
// Store a reference to the microsummary in the menu item, so we know
// which microsummary this menu item represents when it's time to save
// changes to the datastore.
menuItem.microsummary = microsummary;
// Content may have to be generated asynchronously; we don't necessarily
// have it now. If we do, great; otherwise, fall back to the generator
// name, then the URI, and we trigger a microsummary content update.
// Once the update completes, the microsummary will notify our observer
// to rebuild the menu.
// XXX Instead of just showing the generator name or (heaven forbid)
// its URI when we don't have content, we should tell the user that we're
// loading the microsummary, perhaps with some throbbing to let her know
// it's in progress.
if (microsummary.content != null)
menuItem.setAttribute("label", microsummary.content);
else {
menuItem.setAttribute("label", microsummary.generator ? microsummary.generator.name
: microsummary.generatorURI.spec);
microsummary.update();
}
microsummaryMenuPopup.appendChild(menuItem);
// Select the item if this is the current microsummary for the bookmark.
if (this._mss.isMicrosummary(this._bookmarkURI, microsummary))
microsummaryMenuList.selectedItem = menuItem;
}
},
_microsummaryObserver: {
interfaces: [Ci.nsIMicrosummaryObserver, Ci.nsISupports],
QueryInterface: function (iid) {
//if (!this.interfaces.some( function(v) { return iid.equals(v) } ))
if (!iid.equals(Ci.nsIMicrosummaryObserver) &&
!iid.equals(Ci.nsISupports))
throw Components.results.NS_ERROR_NO_INTERFACE;
return this;
},
onContentLoaded: function(microsummary) {
BookmarkPropertiesPanel._rebuildMicrosummaryPicker();
},
onElementAppended: function(microsummary) {
BookmarkPropertiesPanel._rebuildMicrosummaryPicker();
}
},
/**
* Makes a URI from a spec.
* @param spec
* The string spec of the URI
* @returns A URI object for the spec.
*/
_uri: function PC__uri(spec) {
return this._ios.newURI(spec, null, null);
},
/**
* Size the dialog to fit its contents.
*/
_updateSize: function BPP__updateSize() {
var width = this._dialogWindow.outerWidth;
this._dialogWindow.sizeToContent();
this._dialogWindow.resizeTo(width, this._dialogWindow.outerHeight);
},
/**
* This method implements the "Delete Bookmark" action
* in the Bookmark Properties dialog.
*/
dialogDeleteBookmark: function BPP_dialogDeleteBookmark() {
this.deleteBookmark(this._bookmarkURI);
this._hideBookmarkProperties();
},
/**
* This method implements the "Done" action
* in the Bookmark Properties dialog.
*/
dialogDone: function BPP_dialogDone() {
if (this._isMicrosummaryVisible() && this._microsummaries)
this._microsummaries.removeObserver(this._microsummaryObserver);
this._saveChanges();
this._hideBookmarkProperties();
},
/**
* This method deletes the bookmark corresponding to the URI stored
* in bookmarkURI.
*/
deleteBookmark: function BPP_deleteBookmark(bookmarkURI) {
this._assertURINotString(bookmarkURI);
var folders = this._bms.getBookmarkFolders(bookmarkURI, {});
if (folders.length == 0)
return;
var transactions = [];
for (var i = 0; i < folders.length; i++) {
var index = this._bms.indexOfItem(folders[i], bookmarkURI);
var transaction = new PlacesRemoveItemTransaction(bookmarkURI,
folders[i], index)
transactions.push(transaction);
}
var aggregate =
new PlacesAggregateTransaction(this._getDialogTitle(), transactions);
this._controller.tm.doTransaction(aggregate);
},
/**
* This method checks the current state of the input fields in the
* dialog, and if any of them are in an invalid state, it will disable
* the submit button. This method should be called after every
* significant change to the input.
*/
validateChanges: function BPP_validateChanges() {
this._dialogWindow.document.documentElement.getButton("accept").disabled =
!this._inputIsValid();
},
/**
* This method checks to see if the input fields are in a valid state.
*
* @returns true if the input is valid, false otherwise
*/
_inputIsValid: function BPP__inputIsValid() {
// When in multiple select mode, it's possible to deselect all rows,
// but you have to file your bookmark in at least one folder.
if (this._isFolderEditable()) {
if (this._folderTree.getSelectionNodes().length == 0)
return false;
}
if (this._isURIEditable() && !this._containsValidURI("editURLBar"))
return false;
// Feed Location has to be a valid URI;
// Site Location has to be a valid URI or empty
if (this._areLivemarkURIsVisible()) {
if (!this._containsValidURI("editLivemarkFeedLocationBox"))
return false;
if (!this._containsValidURI("editLivemarkSiteLocationBox") &&
(this._element("editLivemarkSiteLocationBox").value.length > 0))
return false;
}
return true;
},
/**
* Determines whether the XUL textbox with the given ID contains a
* string that can be converted into an nsIURI.
*
* @param textboxID the ID of the textbox element whose contents we'll test
*
* @returns true if the textbox contains a valid URI string, false otherwise
*/
_containsValidURI: function BPP__containsValidURI(textboxID) {
try {
var uri = this._uri(this._element(textboxID).value);
} catch (e) {
return false;
}
return true;
},
/**
* Save any changes that might have been made while the properties dialog
* was open.
*/
_saveChanges: function BPP__saveChanges() {
var transactions = [];
var urlbox = this._element("editURLBar");
var titlebox = this._element("editTitleBox");
var newURI = this._bookmarkURI;
if (this._identifierIsURI() && this._isURIEditable())
newURI = this._uri(urlbox.value);
if (this._isFolderEditable()) {
var selected = this._folderTree.getSelectionNodes();
if (this._identifierIsURI()) {
for (var i = 0; i < selected.length; i++) {
var node = selected[i];
if (node.type == node.RESULT_TYPE_FOLDER) {
var folder = node.QueryInterface(Ci.nsINavHistoryFolderResultNode);
if (!folder.childrenReadOnly) {
transactions.push(
new PlacesCreateItemTransaction(newURI, folder.folderId, -1));
}
}
}
}
else if (this._isVariant(this.ADD_MULTIPLE_BOOKMARKS_VARIANT)) {
var node = selected[0];
var folder = node.QueryInterface(Ci.nsINavHistoryFolderResultNode);
var newFolderTrans = new PlacesCreateFolderTransaction(
titlebox.value, folder.folderId, -1);
var childTransactions = [];
for (var i = 0; i < this._URIList.length; ++i) {
var uri = this._URIList[i];
childTransactions.push(
new PlacesCreateItemTransaction(uri, -1, -1));
childTransactions.push(
new PlacesEditItemTitleTransaction(uri,
this._getURITitle(uri)));
}
newFolderTrans.childTransactions = childTransactions;
transactions.push(newFolderTrans);
}
}
if (this._identifierIsURI())
transactions.push(
new PlacesEditItemTitleTransaction(newURI, titlebox.value));
else if (this._identifierIsFolderID()) {
if (this._areLivemarkURIsVisible()) {
if (this._identifierIsFolderID()) {
var feedURIString =
this._element("editLivemarkFeedLocationBox").value;
var feedURI = this._uri(feedURIString);
transactions.push(
new PlacesEditLivemarkFeedURITransaction(this._folderId, feedURI));
// Site Location is empty, we can set its URI to null
var siteURI = null;
var siteURIString =
this._element("editLivemarkSiteLocationBox").value;
if (siteURIString.length > 0)
siteURI = this._uri(siteURIString);
transactions.push(
new PlacesEditLivemarkSiteURITransaction(this._folderId, siteURI));
}
}
transactions.push(
new PlacesEditFolderTitleTransaction(this._folderId, titlebox.value));
}
if (this._isShortcutVisible()) {
var shortcutbox =
this._element("editShortcutBox");
transactions.push(
new PlacesEditBookmarkKeywordTransaction(this._bookmarkURI,
shortcutbox.value));
}
if (this._isVariant(this.EDIT_BOOKMARK_VARIANT) &&
(newURI.spec != this._bookmarkURI.spec)) {
this._controller.changeBookmarkURI(this._bookmarkURI, newURI);
}
if (this._isMicrosummaryVisible()) {
var menuList = document.getElementById("microsummaryMenuList");
// Something should always be selected in the microsummary menu,
// but if nothing is selected, then conservatively assume we should
// just display the bookmark title.
if (menuList.selectedIndex == -1)
menuList.selectedIndex = 0;
// This will set microsummary == undefined if the user selected
// the "don't display a microsummary" item.
var newMicrosummary = menuList.selectedItem.microsummary;
// Only add a microsummary update to the transaction if the microsummary
// has actually changed, i.e. the user selected no microsummary,
// but the bookmark previously had one, or the user selected a microsummary
// which is not the one the bookmark previously had.
if ((newMicrosummary == null &&
this._mss.hasMicrosummary(this._bookmarkURI)) ||
(newMicrosummary != null &&
!this._mss.isMicrosummary(this._bookmarkURI, newMicrosummary))) {
transactions.push(
new PlacesEditBookmarkMicrosummaryTransaction(this._bookmarkURI,
newMicrosummary));
}
}
// If we have any changes to perform, do them via the
// transaction manager in the PlacesController so they can be undone.
if (transactions.length > 0) {
var aggregate =
new PlacesAggregateTransaction(this._getDialogTitle(), transactions);
this._controller.tm.doTransaction(aggregate);
}
},
/**
* This method is called to exit the Bookmark Properties panel.
*/
_hideBookmarkProperties: function BPP__hideBookmarkProperties() {
this._dialogWindow.close();
}
};