diff options
author | estade@chromium.org <estade@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2009-12-14 20:51:29 +0000 |
---|---|---|
committer | estade@chromium.org <estade@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2009-12-14 20:51:29 +0000 |
commit | 216e0bc0a053fe5939f829c877959f9a26a91e11 (patch) | |
tree | 3c9036938d87ee68ba69acc7ca0a9529a19202dd /chrome/browser/extensions | |
parent | a4ed6281fe6d6aad1366a8f6b03e35f6e1eadaa6 (diff) | |
download | chromium_src-216e0bc0a053fe5939f829c877959f9a26a91e11.zip chromium_src-216e0bc0a053fe5939f829c877959f9a26a91e11.tar.gz chromium_src-216e0bc0a053fe5939f829c877959f9a26a91e11.tar.bz2 |
Persist the order of extensions in the browser action toolbar across sessions.
Very similar to what we did with the extension shelf.
BUG=26990
Review URL: http://codereview.chromium.org/487021
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@34490 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser/extensions')
-rw-r--r-- | chrome/browser/extensions/extension_prefs.cc | 31 | ||||
-rw-r--r-- | chrome/browser/extensions/extension_prefs.h | 6 | ||||
-rw-r--r-- | chrome/browser/extensions/extension_toolbar_model.cc | 86 | ||||
-rw-r--r-- | chrome/browser/extensions/extension_toolbar_model.h | 8 |
4 files changed, 122 insertions, 9 deletions
diff --git a/chrome/browser/extensions/extension_prefs.cc b/chrome/browser/extensions/extension_prefs.cc index c793fb3b..aef47ac 100644 --- a/chrome/browser/extensions/extension_prefs.cc +++ b/chrome/browser/extensions/extension_prefs.cc @@ -36,6 +36,11 @@ const wchar_t kPrefBlacklist[] = L"blacklist"; // A preference that tracks extension shelf configuration. This is a list // object read from the Preferences file, containing a list of toolstrip URLs. const wchar_t kExtensionShelf[] = L"extensions.shelf"; + +// A preference that tracks browser action toolbar configuration. This is a list +// object stored in the Preferences file. The extensions are stored by ID. +const wchar_t kExtensionToolbar[] = L"extensions.toolbar"; + } //////////////////////////////////////////////////////////////////////////////// @@ -105,6 +110,8 @@ ExtensionPrefs::ExtensionPrefs(PrefService* prefs, const FilePath& root_dir) prefs_->RegisterDictionaryPref(kExtensionsPref); if (!prefs->FindPreference(kExtensionShelf)) prefs->RegisterListPref(kExtensionShelf); + if (!prefs->FindPreference(kExtensionToolbar)) + prefs->RegisterListPref(kExtensionToolbar); MakePathsRelative(); } @@ -314,6 +321,30 @@ void ExtensionPrefs::SetShelfToolstripOrder(const URLList& urls) { prefs_->ScheduleSavePersistentPrefs(); } +std::vector<std::string> ExtensionPrefs::GetToolbarOrder() { + std::vector<std::string> extension_ids; + const ListValue* toolbar_order = prefs_->GetList(kExtensionToolbar); + if (toolbar_order) { + for (size_t i = 0; i < toolbar_order->GetSize(); ++i) { + std::string extension_id; + if (toolbar_order->GetString(i, &extension_id)) + extension_ids.push_back(extension_id); + } + } + return extension_ids; +} + +void ExtensionPrefs::SetToolbarOrder( + const std::vector<std::string>& extension_ids) { + ListValue* toolbar_order = prefs_->GetMutableList(kExtensionToolbar); + toolbar_order->Clear(); + for (std::vector<std::string>::const_iterator iter = extension_ids.begin(); + iter != extension_ids.end(); ++iter) { + toolbar_order->Append(new StringValue(*iter)); + } + prefs_->ScheduleSavePersistentPrefs(); +} + void ExtensionPrefs::OnExtensionInstalled(Extension* extension) { const std::string& id = extension->id(); // Make sure we don't enable a disabled extension. diff --git a/chrome/browser/extensions/extension_prefs.h b/chrome/browser/extensions/extension_prefs.h index 2bbd239..86ad883 100644 --- a/chrome/browser/extensions/extension_prefs.h +++ b/chrome/browser/extensions/extension_prefs.h @@ -36,6 +36,12 @@ class ExtensionPrefs { // Sets the order that toolstrip URLs appear in the shelf. void SetShelfToolstripOrder(const URLList& urls); + // Get the order that the browser actions appear in the toolbar. + std::vector<std::string> GetToolbarOrder(); + + // Set the order that the browser actions appear in the toolbar. + void SetToolbarOrder(const std::vector<std::string>& extension_ids); + // Called when an extension is installed, so that prefs get created. void OnExtensionInstalled(Extension* extension); diff --git a/chrome/browser/extensions/extension_toolbar_model.cc b/chrome/browser/extensions/extension_toolbar_model.cc index 5a9f2a8..d561120 100644 --- a/chrome/browser/extensions/extension_toolbar_model.cc +++ b/chrome/browser/extensions/extension_toolbar_model.cc @@ -4,6 +4,7 @@ #include "chrome/browser/extensions/extension_toolbar_model.h" +#include "chrome/browser/extensions/extension_prefs.h" #include "chrome/browser/extensions/extensions_service.h" #include "chrome/common/extensions/extension.h" #include "chrome/common/notification_service.h" @@ -46,7 +47,7 @@ void ExtensionToolbarModel::MoveBrowserAction(Extension* extension, bool inserted = false; for (ExtensionList::iterator iter = begin(); iter != end(); ++iter, ++i) { if (i == index) { - toolitems_.insert(pos, extension); + toolitems_.insert(iter, extension); inserted = true; break; } @@ -60,17 +61,15 @@ void ExtensionToolbarModel::MoveBrowserAction(Extension* extension, } FOR_EACH_OBSERVER(Observer, observers_, BrowserActionMoved(extension, index)); + + UpdatePrefs(); } void ExtensionToolbarModel::Observe(NotificationType type, const NotificationSource& source, const NotificationDetails& details) { if (type == NotificationType::EXTENSIONS_READY) { - for (size_t i = 0; i < service_->extensions()->size(); ++i) { - Extension* extension = service_->GetExtensionById( - service_->extensions()->at(i)->id(), false); - AddExtension(extension); - } + InitializeExtensionList(); return; } @@ -96,13 +95,82 @@ void ExtensionToolbarModel::AddExtension(Extension* extension) { toolitems_.push_back(extension); FOR_EACH_OBSERVER(Observer, observers_, BrowserActionAdded(extension, toolitems_.size() - 1)); + + UpdatePrefs(); } void ExtensionToolbarModel::RemoveExtension(Extension* extension) { ExtensionList::iterator pos = std::find(begin(), end(), extension); - if (pos != end()) { - toolitems_.erase(pos); + if (pos == end()) { + return; + } + + toolitems_.erase(pos); + FOR_EACH_OBSERVER(Observer, observers_, + BrowserActionRemoved(extension)); + + UpdatePrefs(); +} + +// Combine the currently enabled extensions that have browser actions (which +// we get from the ExtensionsService) with the ordering we get from the +// pref service. For robustness we use a somewhat inefficient process: +// 1. Create a vector of extensions sorted by their pref values. This vector may +// have holes. +// 2. Create a vector of extensions that did not have a pref value. +// 3. Remove holes from the sorted vector and append the unsorted vector. +void ExtensionToolbarModel::InitializeExtensionList() { + DCHECK(service_->is_ready()); + + std::vector<std::string> pref_order = service_->extension_prefs()-> + GetToolbarOrder(); + // Items that have a pref for their position. + ExtensionList sorted; + sorted.resize(pref_order.size(), NULL); + // The items that don't have a pref for their position. + ExtensionList unsorted; + + // Create the lists. + for (size_t i = 0; i < service_->extensions()->size(); ++i) { + Extension* extension = service_->extensions()->at(i); + if (!extension->browser_action()) + continue; + + std::vector<std::string>::iterator pos = + std::find(pref_order.begin(), pref_order.end(), extension->id()); + if (pos != pref_order.end()) { + int index = std::distance(pref_order.begin(), pos); + sorted[index] = extension; + } else { + unsorted.push_back(extension); + } + } + + // Merge the lists. + toolitems_.reserve(sorted.size() + unsorted.size()); + for (ExtensionList::iterator iter = sorted.begin(); + iter != sorted.end(); ++iter) { + if (*iter != NULL) + toolitems_.push_back(*iter); + } + toolitems_.insert(toolitems_.end(), unsorted.begin(), unsorted.end()); + + // Inform observers. + for (size_t i = 0; i < toolitems_.size(); i++) { FOR_EACH_OBSERVER(Observer, observers_, - BrowserActionRemoved(extension)); + BrowserActionAdded(toolitems_[i], i)); } + + UpdatePrefs(); +} + +void ExtensionToolbarModel::UpdatePrefs() { + if (!service_->extension_prefs()) + return; + + std::vector<std::string> ids; + ids.reserve(toolitems_.size()); + for (ExtensionList::iterator iter = begin(); iter != end(); ++iter) + ids.push_back((*iter)->id()); + service_->extension_prefs()->SetToolbarOrder(ids); } diff --git a/chrome/browser/extensions/extension_toolbar_model.h b/chrome/browser/extensions/extension_toolbar_model.h index 54977eb..5b6a8a4 100644 --- a/chrome/browser/extensions/extension_toolbar_model.h +++ b/chrome/browser/extensions/extension_toolbar_model.h @@ -52,6 +52,14 @@ class ExtensionToolbarModel : public NotificationObserver { const NotificationSource& source, const NotificationDetails& details); + // To be called after the extension service is ready; gets loaded extensions + // from the extension service and their saved order from the pref service + // and constructs |toolitems_| from these data. + void InitializeExtensionList(); + + // Save the model to prefs. + void UpdatePrefs(); + // Our observers. ObserverList<Observer> observers_; |