| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "chrome/browser/ui/ash/launcher/chrome_launcher_controller.h" | 5 #include "chrome/browser/ui/ash/launcher/chrome_launcher_controller.h" |
| 6 | 6 |
| 7 #include <set> | 7 #include <set> |
| 8 #include <vector> | 8 #include <vector> |
| 9 | 9 |
| 10 #include "ash/launcher/launcher_model.h" | 10 #include "ash/launcher/launcher_model.h" |
| (...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 117 | 117 |
| 118 // Stores the optional refocus url pattern for this item. | 118 // Stores the optional refocus url pattern for this item. |
| 119 const GURL& refocus_url() const { return refocus_url_; } | 119 const GURL& refocus_url() const { return refocus_url_; } |
| 120 void set_refocus_url(const GURL& refocus_url) { refocus_url_ = refocus_url; } | 120 void set_refocus_url(const GURL& refocus_url) { refocus_url_ = refocus_url; } |
| 121 | 121 |
| 122 private: | 122 private: |
| 123 GURL refocus_url_; | 123 GURL refocus_url_; |
| 124 DISALLOW_COPY_AND_ASSIGN(AppShortcutLauncherItemController); | 124 DISALLOW_COPY_AND_ASSIGN(AppShortcutLauncherItemController); |
| 125 }; | 125 }; |
| 126 | 126 |
| 127 // If the value of the pref at |local_path is not empty, it is returned |
| 128 // otherwise the value of the pref at |synced_path| is returned. |
| 129 std::string GetLocalOrRemotePref(PrefService* pref_service, |
| 130 const char* local_path, |
| 131 const char* synced_path) { |
| 132 const std::string value(pref_service->GetString(local_path)); |
| 133 return value.empty() ? pref_service->GetString(synced_path) : value; |
| 134 } |
| 135 |
| 136 // If prefs have synced and the pref value at |local_path| is empty the value |
| 137 // from |synced_path| is copied to |local_path|. |
| 138 void MaybePropagatePrefToLocal(PrefService* pref_service, |
| 139 const char* local_path, |
| 140 const char* synced_path) { |
| 141 if (pref_service->GetString(local_path).empty() && |
| 142 pref_service->HasSynced()) { |
| 143 // First time the user is using this machine, propagate from remote to |
| 144 // local. |
| 145 pref_service->SetString(local_path, pref_service->GetString(synced_path)); |
| 146 } |
| 147 } |
| 148 |
| 127 } // namespace | 149 } // namespace |
| 128 | 150 |
| 129 // ChromeLauncherController ---------------------------------------------------- | 151 // ChromeLauncherController ---------------------------------------------------- |
| 130 | 152 |
| 131 // statics | 153 // statics |
| 132 ChromeLauncherController* ChromeLauncherController::instance_ = NULL; | 154 ChromeLauncherController* ChromeLauncherController::instance_ = NULL; |
| 133 | 155 |
| 134 ChromeLauncherController::ChromeLauncherController(Profile* profile, | 156 ChromeLauncherController::ChromeLauncherController(Profile* profile, |
| 135 ash::LauncherModel* model) | 157 ash::LauncherModel* model) |
| 136 : model_(model), | 158 : model_(model), |
| (...skipping 24 matching lines...) Expand all Loading... |
| 161 app_icon_loader_.reset(new LauncherAppIconLoader(profile_, this)); | 183 app_icon_loader_.reset(new LauncherAppIconLoader(profile_, this)); |
| 162 | 184 |
| 163 notification_registrar_.Add(this, | 185 notification_registrar_.Add(this, |
| 164 chrome::NOTIFICATION_EXTENSION_LOADED, | 186 chrome::NOTIFICATION_EXTENSION_LOADED, |
| 165 content::Source<Profile>(profile_)); | 187 content::Source<Profile>(profile_)); |
| 166 notification_registrar_.Add(this, | 188 notification_registrar_.Add(this, |
| 167 chrome::NOTIFICATION_EXTENSION_UNLOADED, | 189 chrome::NOTIFICATION_EXTENSION_UNLOADED, |
| 168 content::Source<Profile>(profile_)); | 190 content::Source<Profile>(profile_)); |
| 169 pref_change_registrar_.Init(profile_->GetPrefs()); | 191 pref_change_registrar_.Init(profile_->GetPrefs()); |
| 170 pref_change_registrar_.Add(prefs::kPinnedLauncherApps, this); | 192 pref_change_registrar_.Add(prefs::kPinnedLauncherApps, this); |
| 171 pref_change_registrar_.Add(prefs::kShelfAlignment, this); | |
| 172 pref_change_registrar_.Add(prefs::kShelfAutoHideBehavior, this); | |
| 173 } | 193 } |
| 174 | 194 |
| 175 ChromeLauncherController::~ChromeLauncherController() { | 195 ChromeLauncherController::~ChromeLauncherController() { |
| 176 // Reset the shell window controller here since it has a weak pointer to this. | 196 // Reset the shell window controller here since it has a weak pointer to this. |
| 177 shell_window_controller_.reset(); | 197 shell_window_controller_.reset(); |
| 178 | 198 |
| 179 model_->RemoveObserver(this); | 199 model_->RemoveObserver(this); |
| 180 for (IDToItemControllerMap::iterator i = id_to_item_controller_map_.begin(); | 200 for (IDToItemControllerMap::iterator i = id_to_item_controller_map_.begin(); |
| 181 i != id_to_item_controller_map_.end(); ++i) { | 201 i != id_to_item_controller_map_.end(); ++i) { |
| 182 i->second->OnRemoved(); | 202 i->second->OnRemoved(); |
| 183 model_->RemoveItemAt(model_->ItemIndexByID(i->first)); | 203 model_->RemoveItemAt(model_->ItemIndexByID(i->first)); |
| 184 } | 204 } |
| 185 if (instance_ == this) | 205 if (instance_ == this) |
| 186 instance_ = NULL; | 206 instance_ = NULL; |
| 187 | 207 |
| 188 if (ash::Shell::HasInstance()) | 208 if (ash::Shell::HasInstance()) |
| 189 ash::Shell::GetInstance()->RemoveShellObserver(this); | 209 ash::Shell::GetInstance()->RemoveShellObserver(this); |
| 190 | 210 |
| 191 if (observed_sync_service_) | 211 if (observed_sync_service_) |
| 192 observed_sync_service_->RemoveObserver(this); | 212 observed_sync_service_->RemoveObserver(this); |
| 213 |
| 214 profile_->GetPrefs()->RemoveObserver(this); |
| 193 } | 215 } |
| 194 | 216 |
| 195 void ChromeLauncherController::Init() { | 217 void ChromeLauncherController::Init() { |
| 196 // TODO(xiyuan): Remove migration code and kUseDefaultPinnedApp after M20. | 218 // TODO(xiyuan): Remove migration code and kUseDefaultPinnedApp after M20. |
| 197 // Migration cases: | 219 // Migration cases: |
| 198 // - Users that unpin all apps: | 220 // - Users that unpin all apps: |
| 199 // - have default pinned apps | 221 // - have default pinned apps |
| 200 // - kUseDefaultPinnedApps set to false | 222 // - kUseDefaultPinnedApps set to false |
| 201 // Migrate them by setting an empty list for kPinnedLauncherApps. | 223 // Migrate them by setting an empty list for kPinnedLauncherApps. |
| 202 // | 224 // |
| (...skipping 12 matching lines...) Expand all Loading... |
| 215 ListPrefUpdate updater(profile_->GetPrefs(), prefs::kPinnedLauncherApps); | 237 ListPrefUpdate updater(profile_->GetPrefs(), prefs::kPinnedLauncherApps); |
| 216 updater.Get()->Clear(); | 238 updater.Get()->Clear(); |
| 217 } | 239 } |
| 218 | 240 |
| 219 UpdateAppLaunchersFromPref(); | 241 UpdateAppLaunchersFromPref(); |
| 220 | 242 |
| 221 // TODO(sky): update unit test so that this test isn't necessary. | 243 // TODO(sky): update unit test so that this test isn't necessary. |
| 222 if (ash::Shell::HasInstance()) { | 244 if (ash::Shell::HasInstance()) { |
| 223 SetShelfAutoHideBehaviorFromPrefs(); | 245 SetShelfAutoHideBehaviorFromPrefs(); |
| 224 SetShelfAlignmentFromPrefs(); | 246 SetShelfAlignmentFromPrefs(); |
| 247 PrefService* prefs = profile_->GetPrefs(); |
| 248 if (prefs->GetString(prefs::kShelfAlignmentLocal).empty() || |
| 249 prefs->GetString(prefs::kShelfAutoHideBehaviorLocal).empty()) { |
| 250 prefs->AddObserver(this); |
| 251 } |
| 225 ash::Shell::GetInstance()->AddShellObserver(this); | 252 ash::Shell::GetInstance()->AddShellObserver(this); |
| 226 } | 253 } |
| 227 } | 254 } |
| 228 | 255 |
| 229 ash::LauncherID ChromeLauncherController::CreateTabbedLauncherItem( | 256 ash::LauncherID ChromeLauncherController::CreateTabbedLauncherItem( |
| 230 LauncherItemController* controller, | 257 LauncherItemController* controller, |
| 231 IncognitoState is_incognito, | 258 IncognitoState is_incognito, |
| 232 ash::LauncherItemStatus status) { | 259 ash::LauncherItemStatus status) { |
| 233 ash::LauncherID id = model_->next_id(); | 260 ash::LauncherID id = model_->next_id(); |
| 234 DCHECK(!HasItemController(id)); | 261 DCHECK(!HasItemController(id)); |
| (...skipping 311 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 546 ash::Shell::GetInstance()->SetShelfAutoHideBehavior(behavior); | 573 ash::Shell::GetInstance()->SetShelfAutoHideBehavior(behavior); |
| 547 const char* value = NULL; | 574 const char* value = NULL; |
| 548 switch (behavior) { | 575 switch (behavior) { |
| 549 case ash::SHELF_AUTO_HIDE_BEHAVIOR_ALWAYS: | 576 case ash::SHELF_AUTO_HIDE_BEHAVIOR_ALWAYS: |
| 550 value = ash::kShelfAutoHideBehaviorAlways; | 577 value = ash::kShelfAutoHideBehaviorAlways; |
| 551 break; | 578 break; |
| 552 case ash::SHELF_AUTO_HIDE_BEHAVIOR_NEVER: | 579 case ash::SHELF_AUTO_HIDE_BEHAVIOR_NEVER: |
| 553 value = ash::kShelfAutoHideBehaviorNever; | 580 value = ash::kShelfAutoHideBehaviorNever; |
| 554 break; | 581 break; |
| 555 } | 582 } |
| 583 // See comment in |kShelfAlignment| about why we have two prefs here. |
| 584 profile_->GetPrefs()->SetString(prefs::kShelfAutoHideBehaviorLocal, value); |
| 556 profile_->GetPrefs()->SetString(prefs::kShelfAutoHideBehavior, value); | 585 profile_->GetPrefs()->SetString(prefs::kShelfAutoHideBehavior, value); |
| 557 } | 586 } |
| 558 | 587 |
| 559 void ChromeLauncherController::RemoveTabFromRunningApp( | 588 void ChromeLauncherController::RemoveTabFromRunningApp( |
| 560 TabContents* tab, | 589 TabContents* tab, |
| 561 const std::string& app_id) { | 590 const std::string& app_id) { |
| 562 tab_contents_to_app_id_.erase(tab); | 591 tab_contents_to_app_id_.erase(tab); |
| 563 AppIDToTabContentsListMap::iterator i_app_id = | 592 AppIDToTabContentsListMap::iterator i_app_id = |
| 564 app_id_to_tab_contents_list_.find(app_id); | 593 app_id_to_tab_contents_list_.find(app_id); |
| 565 if (i_app_id != app_id_to_tab_contents_list_.end()) { | 594 if (i_app_id != app_id_to_tab_contents_list_.end()) { |
| (...skipping 180 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 746 details); | 775 details); |
| 747 const Extension* extension = unload_info->extension; | 776 const Extension* extension = unload_info->extension; |
| 748 if (IsAppPinned(extension->id())) | 777 if (IsAppPinned(extension->id())) |
| 749 DoUnpinAppsWithID(extension->id()); | 778 DoUnpinAppsWithID(extension->id()); |
| 750 app_icon_loader_->ClearImage(extension->id()); | 779 app_icon_loader_->ClearImage(extension->id()); |
| 751 break; | 780 break; |
| 752 } | 781 } |
| 753 case chrome::NOTIFICATION_PREF_CHANGED: { | 782 case chrome::NOTIFICATION_PREF_CHANGED: { |
| 754 const std::string& pref_name( | 783 const std::string& pref_name( |
| 755 *content::Details<std::string>(details).ptr()); | 784 *content::Details<std::string>(details).ptr()); |
| 756 if (pref_name == prefs::kPinnedLauncherApps) | 785 if (pref_name == prefs::kPinnedLauncherApps) { |
| 757 UpdateAppLaunchersFromPref(); | 786 UpdateAppLaunchersFromPref(); |
| 758 else if (pref_name == prefs::kShelfAlignment) | 787 } else if (pref_name == prefs::kShelfAlignmentLocal) { |
| 759 SetShelfAlignmentFromPrefs(); | 788 SetShelfAlignmentFromPrefs(); |
| 760 else if (pref_name == prefs::kShelfAutoHideBehavior) | 789 } else if (pref_name == prefs::kShelfAutoHideBehaviorLocal) { |
| 761 SetShelfAutoHideBehaviorFromPrefs(); | 790 SetShelfAutoHideBehaviorFromPrefs(); |
| 762 else | 791 } else { |
| 763 NOTREACHED() << "Unexpected pref change for " << pref_name; | 792 NOTREACHED() << "Unexpected pref change for " << pref_name; |
| 793 } |
| 764 break; | 794 break; |
| 765 } | 795 } |
| 766 default: | 796 default: |
| 767 NOTREACHED() << "Unexpected notification type=" << type; | 797 NOTREACHED() << "Unexpected notification type=" << type; |
| 768 } | 798 } |
| 769 } | 799 } |
| 770 | 800 |
| 771 void ChromeLauncherController::OnShelfAlignmentChanged() { | 801 void ChromeLauncherController::OnShelfAlignmentChanged() { |
| 772 const char* pref_value = NULL; | 802 const char* pref_value = NULL; |
| 773 switch (ash::Shell::GetInstance()->GetShelfAlignment()) { | 803 switch (ash::Shell::GetInstance()->GetShelfAlignment()) { |
| 774 case ash::SHELF_ALIGNMENT_BOTTOM: | 804 case ash::SHELF_ALIGNMENT_BOTTOM: |
| 775 pref_value = ash::kShelfAlignmentBottom; | 805 pref_value = ash::kShelfAlignmentBottom; |
| 776 break; | 806 break; |
| 777 case ash::SHELF_ALIGNMENT_LEFT: | 807 case ash::SHELF_ALIGNMENT_LEFT: |
| 778 pref_value = ash::kShelfAlignmentLeft; | 808 pref_value = ash::kShelfAlignmentLeft; |
| 779 break; | 809 break; |
| 780 case ash::SHELF_ALIGNMENT_RIGHT: | 810 case ash::SHELF_ALIGNMENT_RIGHT: |
| 781 pref_value = ash::kShelfAlignmentRight; | 811 pref_value = ash::kShelfAlignmentRight; |
| 782 break; | 812 break; |
| 783 } | 813 } |
| 814 // See comment in |kShelfAlignment| about why we have two prefs here. |
| 815 profile_->GetPrefs()->SetString(prefs::kShelfAlignmentLocal, pref_value); |
| 784 profile_->GetPrefs()->SetString(prefs::kShelfAlignment, pref_value); | 816 profile_->GetPrefs()->SetString(prefs::kShelfAlignment, pref_value); |
| 785 } | 817 } |
| 786 | 818 |
| 787 void ChromeLauncherController::OnStateChanged() { | 819 void ChromeLauncherController::OnStateChanged() { |
| 788 DCHECK(observed_sync_service_); | 820 DCHECK(observed_sync_service_); |
| 789 CheckAppSync(); | 821 CheckAppSync(); |
| 790 } | 822 } |
| 791 | 823 |
| 824 void ChromeLauncherController::OnHasSyncedChanged() { |
| 825 MaybePropagatePrefToLocal(profile_->GetPrefs(), |
| 826 prefs::kShelfAlignmentLocal, |
| 827 prefs::kShelfAlignment); |
| 828 MaybePropagatePrefToLocal(profile_->GetPrefs(), |
| 829 prefs::kShelfAutoHideBehaviorLocal, |
| 830 prefs::kShelfAutoHideBehavior); |
| 831 } |
| 832 |
| 792 void ChromeLauncherController::PersistPinnedState() { | 833 void ChromeLauncherController::PersistPinnedState() { |
| 793 // It is a coding error to call PersistPinnedState() if the pinned apps are | 834 // It is a coding error to call PersistPinnedState() if the pinned apps are |
| 794 // not user-editable. The code should check earlier and not perform any | 835 // not user-editable. The code should check earlier and not perform any |
| 795 // modification actions that trigger persisting the state. | 836 // modification actions that trigger persisting the state. |
| 796 if (!CanPin()) { | 837 if (!CanPin()) { |
| 797 NOTREACHED() << "Can't pin but pinned state being updated"; | 838 NOTREACHED() << "Can't pin but pinned state being updated"; |
| 798 return; | 839 return; |
| 799 } | 840 } |
| 800 | 841 |
| 801 // Set kUseDefaultPinnedApps to false and use pinned apps list from prefs | 842 // Set kUseDefaultPinnedApps to false and use pinned apps list from prefs |
| (...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 935 else | 976 else |
| 936 ++index; | 977 ++index; |
| 937 } | 978 } |
| 938 | 979 |
| 939 // Append unprocessed items from the pref to the end of the model. | 980 // Append unprocessed items from the pref to the end of the model. |
| 940 for (; pref_app_id != pinned_apps.end(); ++pref_app_id) | 981 for (; pref_app_id != pinned_apps.end(); ++pref_app_id) |
| 941 DoPinAppWithID(*pref_app_id); | 982 DoPinAppWithID(*pref_app_id); |
| 942 } | 983 } |
| 943 | 984 |
| 944 void ChromeLauncherController::SetShelfAutoHideBehaviorFromPrefs() { | 985 void ChromeLauncherController::SetShelfAutoHideBehaviorFromPrefs() { |
| 986 // See comment in |kShelfAlignment| as to why we consider two prefs. |
| 987 const std::string behavior_value( |
| 988 GetLocalOrRemotePref(profile_->GetPrefs(), |
| 989 prefs::kShelfAutoHideBehaviorLocal, |
| 990 prefs::kShelfAutoHideBehavior)); |
| 991 |
| 945 // Note: To maintain sync compatibility with old images of chrome/chromeos | 992 // Note: To maintain sync compatibility with old images of chrome/chromeos |
| 946 // the set of values that may be encountered includes the now-extinct | 993 // the set of values that may be encountered includes the now-extinct |
| 947 // "Default" as well as "Never" and "Always", "Default" should now | 994 // "Default" as well as "Never" and "Always", "Default" should now |
| 948 // be treated as "Never". | 995 // be treated as "Never". |
| 949 // (http://code.google.com/p/chromium/issues/detail?id=146773) | 996 // (http://code.google.com/p/chromium/issues/detail?id=146773) |
| 950 const std::string behavior_value( | |
| 951 profile_->GetPrefs()->GetString(prefs::kShelfAutoHideBehavior)); | |
| 952 ash::ShelfAutoHideBehavior behavior = | 997 ash::ShelfAutoHideBehavior behavior = |
| 953 ash::SHELF_AUTO_HIDE_BEHAVIOR_NEVER; | 998 ash::SHELF_AUTO_HIDE_BEHAVIOR_NEVER; |
| 954 if (behavior_value == ash::kShelfAutoHideBehaviorAlways) | 999 if (behavior_value == ash::kShelfAutoHideBehaviorAlways) |
| 955 behavior = ash::SHELF_AUTO_HIDE_BEHAVIOR_ALWAYS; | 1000 behavior = ash::SHELF_AUTO_HIDE_BEHAVIOR_ALWAYS; |
| 956 ash::Shell::GetInstance()->SetShelfAutoHideBehavior(behavior); | 1001 ash::Shell::GetInstance()->SetShelfAutoHideBehavior(behavior); |
| 957 } | 1002 } |
| 958 | 1003 |
| 959 void ChromeLauncherController::SetShelfAlignmentFromPrefs() { | 1004 void ChromeLauncherController::SetShelfAlignmentFromPrefs() { |
| 960 if (!CommandLine::ForCurrentProcess()->HasSwitch( | 1005 if (!CommandLine::ForCurrentProcess()->HasSwitch( |
| 961 switches::kShowLauncherAlignmentMenu)) | 1006 switches::kShowLauncherAlignmentMenu)) |
| 962 return; | 1007 return; |
| 963 | 1008 |
| 1009 // See comment in |kShelfAlignment| as to why we consider two prefs. |
| 964 const std::string alignment_value( | 1010 const std::string alignment_value( |
| 965 profile_->GetPrefs()->GetString(prefs::kShelfAlignment)); | 1011 GetLocalOrRemotePref(profile_->GetPrefs(), |
| 1012 prefs::kShelfAlignmentLocal, |
| 1013 prefs::kShelfAlignment)); |
| 966 ash::ShelfAlignment alignment = ash::SHELF_ALIGNMENT_BOTTOM; | 1014 ash::ShelfAlignment alignment = ash::SHELF_ALIGNMENT_BOTTOM; |
| 967 if (alignment_value == ash::kShelfAlignmentLeft) | 1015 if (alignment_value == ash::kShelfAlignmentLeft) |
| 968 alignment = ash::SHELF_ALIGNMENT_LEFT; | 1016 alignment = ash::SHELF_ALIGNMENT_LEFT; |
| 969 else if (alignment_value == ash::kShelfAlignmentRight) | 1017 else if (alignment_value == ash::kShelfAlignmentRight) |
| 970 alignment = ash::SHELF_ALIGNMENT_RIGHT; | 1018 alignment = ash::SHELF_ALIGNMENT_RIGHT; |
| 1019 |
| 971 ash::Shell::GetInstance()->SetShelfAlignment(alignment); | 1020 ash::Shell::GetInstance()->SetShelfAlignment(alignment); |
| 972 } | 1021 } |
| 973 | 1022 |
| 974 TabContents* ChromeLauncherController::GetLastActiveTabContents( | 1023 TabContents* ChromeLauncherController::GetLastActiveTabContents( |
| 975 const std::string& app_id) { | 1024 const std::string& app_id) { |
| 976 AppIDToTabContentsListMap::const_iterator i = | 1025 AppIDToTabContentsListMap::const_iterator i = |
| 977 app_id_to_tab_contents_list_.find(app_id); | 1026 app_id_to_tab_contents_list_.find(app_id); |
| 978 if (i == app_id_to_tab_contents_list_.end()) | 1027 if (i == app_id_to_tab_contents_list_.end()) |
| 979 return NULL; | 1028 return NULL; |
| 980 DCHECK_GT(i->second.size(), 0u); | 1029 DCHECK_GT(i->second.size(), 0u); |
| (...skipping 80 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1061 } | 1110 } |
| 1062 | 1111 |
| 1063 void ChromeLauncherController::StopLoadingAnimation() { | 1112 void ChromeLauncherController::StopLoadingAnimation() { |
| 1064 DCHECK(observed_sync_service_); | 1113 DCHECK(observed_sync_service_); |
| 1065 | 1114 |
| 1066 model_->SetStatus(ash::LauncherModel::STATUS_NORMAL); | 1115 model_->SetStatus(ash::LauncherModel::STATUS_NORMAL); |
| 1067 loading_timer_.Stop(); | 1116 loading_timer_.Stop(); |
| 1068 observed_sync_service_->RemoveObserver(this); | 1117 observed_sync_service_->RemoveObserver(this); |
| 1069 observed_sync_service_ = NULL; | 1118 observed_sync_service_ = NULL; |
| 1070 } | 1119 } |
| OLD | NEW |