diff --git a/browser/components/places/content/controller.js b/browser/components/places/content/controller.js
index 0d4e039b5d02..7c5ebe14a588 100755
--- a/browser/components/places/content/controller.js
+++ b/browser/components/places/content/controller.js
@@ -519,7 +519,12 @@ var PlacesController = {
*/
nodeIsRemoteContainer: function PC_nodeIsRemoteContainer(node) {
const NHRN = Ci.nsINavHistoryResultNode;
- return node.type == NHRN.RESULT_TYPE_REMOTE_CONTAINER;
+ if (node.type == NHRN.RESULT_TYPE_REMOTE_CONTAINER)
+ return true;
+ if (node.type == NHRN.RESULT_TYPE_FOLDER)
+ return asFolder(node).folderType != "";
+
+ return false;
},
/**
diff --git a/browser/components/places/content/menu.xml b/browser/components/places/content/menu.xml
index f05bdc3ec2bd..b0e406045c3b 100755
--- a/browser/components/places/content/menu.xml
+++ b/browser/components/places/content/menu.xml
@@ -92,7 +92,6 @@
element.setAttribute("label", child.title);
element.setAttribute("url", child.QueryInterface(Ci.nsINavHistoryURIResultNode).uri);
element.setAttribute("statustext", child.url);
- element.setAttribute("image", child.icon.spec);
element.className = "menuitem-iconic bookmark-item";
}
else if (PlacesController.nodeIsContainer(child)) {
@@ -115,6 +114,8 @@
element.node = child;
this.appendChild(element);
}
+ if (child.icon)
+ element.setAttribute("image", child.icon.spec);
}
} else {
var bundle = document.getElementById("placeBundle");
@@ -202,7 +203,7 @@
- false
+ false
[TYPE_X_MOZ_PLACE_CONTAINER, TYPE_X_MOZ_PLACE, TYPE_X_MOZ_URL]
diff --git a/browser/components/places/content/toolbar.xml b/browser/components/places/content/toolbar.xml
index fb3d1050c996..d0b41192ddf1 100755
--- a/browser/components/places/content/toolbar.xml
+++ b/browser/components/places/content/toolbar.xml
@@ -54,7 +54,7 @@
null
-
- false
+ false
[TYPE_X_MOZ_PLACE_CONTAINER, TYPE_X_MOZ_PLACE, TYPE_X_MOZ_URL]
@@ -267,50 +265,57 @@
BeginUpdateBatch();
rv = TryParseAsRDF();
// Try parsing as Atom/Simple RSS
@@ -248,6 +249,7 @@ nsLivemarkLoadListener::OnStopRequest(nsIRequest *aRequest,
if (!NS_SUCCEEDED(rv)) {
rv = mLivemarkService->InsertLivemarkFailedItem(mLivemark->folderId);
}
+ mLivemarkService->EndUpdateBatch();
// Set an expiration on the livemark, for reloading the data
PRInt32 ttl;
diff --git a/browser/components/places/src/nsLivemarkService.cpp b/browser/components/places/src/nsLivemarkService.cpp
index 02c4a57419e3..a76f5e78e396 100755
--- a/browser/components/places/src/nsLivemarkService.cpp
+++ b/browser/components/places/src/nsLivemarkService.cpp
@@ -41,6 +41,7 @@
#include "nsNavBookmarks.h"
#include "nsNavHistoryResult.h"
#include "nsIAnnotationService.h"
+#include "nsFaviconService.h"
#include "nsNetUtil.h"
#include "rdf.h"
#include "nsIRDFService.h"
@@ -48,6 +49,7 @@
#define LIVEMARK_TIMEOUT 15000 // fire every 15 seconds
#define PLACES_STRING_BUNDLE_URI "chrome://browser/locale/places/places.properties"
+#define LIVEMARK_ICON_URI "chrome://browser/skin/places/livemark_item.png"
// Constants for parsing RDF Livemarks
// These are used in nsBookmarksFeedHandler.cpp, but because there is
@@ -122,6 +124,10 @@ nsLivemarkService::Init()
getter_AddRefs(mBundle));
NS_ENSURE_SUCCESS(rv, rv);
+ // Initialize the folder icon uri.
+ rv = NS_NewURI(getter_AddRefs(mIconURI), NS_LITERAL_STRING(LIVEMARK_ICON_URI));
+ NS_ENSURE_SUCCESS(rv, rv);
+
// Initialize the localized strings for the names of the dummy
// "livemark loading..." and "livemark failed to load" bookmarks
rv = mBundle->GetStringFromName(NS_LITERAL_STRING("bookmarksLivemarkLoading").get(),
@@ -257,6 +263,11 @@ nsLivemarkService::CreateLivemark(PRInt64 aFolder,
0,
nsIAnnotationService::EXPIRE_NEVER);
+ // Set the icon for the livemark
+ nsFaviconService* faviconService = nsFaviconService::GetFaviconService();
+ NS_ENSURE_TRUE(faviconService, NS_ERROR_OUT_OF_MEMORY);
+ faviconService->SetFaviconUrlForPage(livemarkURI, mIconURI);
+
if (aSiteURI) {
// Add an annotation to map the folder URI to the livemark site URI
nsCAutoString siteURISpec;
@@ -495,6 +506,22 @@ nsLivemarkService::DeleteLivemarkChildren(PRInt64 aLivemarkFolderId)
return rv;
}
+nsresult
+nsLivemarkService::BeginUpdateBatch()
+{
+ nsNavBookmarks *bookmarks = nsNavBookmarks::GetBookmarksService();
+ NS_ENSURE_TRUE(bookmarks, NS_ERROR_OUT_OF_MEMORY);
+ return bookmarks->BeginUpdateBatch();
+}
+
+nsresult
+nsLivemarkService::EndUpdateBatch()
+{
+ nsNavBookmarks *bookmarks = nsNavBookmarks::GetBookmarksService();
+ NS_ENSURE_TRUE(bookmarks, NS_ERROR_OUT_OF_MEMORY);
+ return bookmarks->EndUpdateBatch();
+}
+
nsresult
nsLivemarkService::InsertLivemarkChild(PRInt64 aLivemarkFolderId,
nsIURI *aURI,
diff --git a/browser/components/places/src/nsLivemarkService.h b/browser/components/places/src/nsLivemarkService.h
index 0a5f448ceb8a..83ab86ce756c 100755
--- a/browser/components/places/src/nsLivemarkService.h
+++ b/browser/components/places/src/nsLivemarkService.h
@@ -61,6 +61,8 @@ public:
// These functions are called by the livemarks feed loader
// to set the livemark children.
+ nsresult BeginUpdateBatch();
+ nsresult EndUpdateBatch();
nsresult DeleteLivemarkChildren(PRInt64 aLivemarkFolderId);
nsresult InsertLivemarkChild(PRInt64 aLivemarkFolderId,
nsIURI *aURI,
@@ -105,6 +107,8 @@ private:
nsXPIDLString mLivemarkLoading;
nsXPIDLString mLivemarkFailed;
+ nsCOMPtr mIconURI;
+
nsCOMPtr mAnnotationService;
nsCOMPtr mBookmarksService;
diff --git a/browser/components/places/src/nsNavHistoryResult.cpp b/browser/components/places/src/nsNavHistoryResult.cpp
index dde6c721002a..ee9634b6eb40 100755
--- a/browser/components/places/src/nsNavHistoryResult.cpp
+++ b/browser/components/places/src/nsNavHistoryResult.cpp
@@ -108,6 +108,10 @@ nsNavHistoryResultNode::GetIcon(nsIURI** aURI)
{
nsFaviconService* faviconService = nsFaviconService::GetFaviconService();
NS_ENSURE_TRUE(faviconService, NS_ERROR_NO_INTERFACE);
+ if (mFaviconURI.IsEmpty()) {
+ *aURI = nsnull;
+ return NS_OK;
+ }
return faviconService->GetFaviconLinkForIconString(mFaviconURI, aURI);
}