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/themes/theme_service.h" | 5 #include "chrome/browser/themes/theme_service.h" |
6 | 6 |
7 #include "base/bind.h" | 7 #include "base/bind.h" |
8 #include "base/memory/ref_counted_memory.h" | 8 #include "base/memory/ref_counted_memory.h" |
9 #include "base/sequenced_task_runner.h" | 9 #include "base/sequenced_task_runner.h" |
10 #include "base/string_split.h" | 10 #include "base/string_split.h" |
(...skipping 206 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
217 } | 217 } |
218 | 218 |
219 ThemeService::~ThemeService() { | 219 ThemeService::~ThemeService() { |
220 FreePlatformCaches(); | 220 FreePlatformCaches(); |
221 } | 221 } |
222 | 222 |
223 void ThemeService::Init(Profile* profile) { | 223 void ThemeService::Init(Profile* profile) { |
224 DCHECK(CalledOnValidThread()); | 224 DCHECK(CalledOnValidThread()); |
225 profile_ = profile; | 225 profile_ = profile; |
226 | 226 |
| 227 // Listen to EXTENSION_LOADED instead of EXTENSION_INSTALLED because |
| 228 // the extension cannot yet be found via GetExtensionById() if it is |
| 229 // installed but not loaded (which may confuse listeners to |
| 230 // BROWSER_THEME_CHANGED). |
| 231 registrar_.Add(this, |
| 232 chrome::NOTIFICATION_EXTENSION_LOADED, |
| 233 content::Source<Profile>(profile_)); |
| 234 |
227 LoadThemePrefs(); | 235 LoadThemePrefs(); |
228 | 236 |
229 theme_syncable_service_.reset(new ThemeSyncableService(profile_, this)); | 237 theme_syncable_service_.reset(new ThemeSyncableService(profile_, this)); |
230 } | 238 } |
231 | 239 |
232 gfx::Image ThemeService::GetImageNamed(int id) const { | 240 gfx::Image ThemeService::GetImageNamed(int id) const { |
233 DCHECK(CalledOnValidThread()); | 241 DCHECK(CalledOnValidThread()); |
234 | 242 |
235 const gfx::Image* image = NULL; | 243 const gfx::Image* image = NULL; |
236 | 244 |
(...skipping 98 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
335 } | 343 } |
336 | 344 |
337 void ThemeService::SetTheme(const Extension* extension) { | 345 void ThemeService::SetTheme(const Extension* extension) { |
338 // Clear our image cache. | 346 // Clear our image cache. |
339 FreePlatformCaches(); | 347 FreePlatformCaches(); |
340 | 348 |
341 DCHECK(extension); | 349 DCHECK(extension); |
342 DCHECK(extension->is_theme()); | 350 DCHECK(extension->is_theme()); |
343 | 351 |
344 BuildFromExtension(extension); | 352 BuildFromExtension(extension); |
345 SaveThemeIDForProfile(profile_, extension->id()); | 353 SaveThemeID(extension->id()); |
346 | 354 |
347 NotifyThemeChanged(); | 355 NotifyThemeChanged(); |
348 content::RecordAction(UserMetricsAction("Themes_Installed")); | 356 content::RecordAction(UserMetricsAction("Themes_Installed")); |
349 } | 357 } |
350 | 358 |
| 359 void ThemeService::RemoveUnusedThemes() { |
| 360 if (!profile_) |
| 361 return; |
| 362 ExtensionService* service = profile_->GetExtensionService(); |
| 363 if (!service) |
| 364 return; |
| 365 std::string current_theme = GetThemeID(); |
| 366 std::vector<std::string> remove_list; |
| 367 const ExtensionSet* extensions = service->extensions(); |
| 368 for (ExtensionSet::const_iterator it = extensions->begin(); |
| 369 it != extensions->end(); ++it) { |
| 370 if ((*it)->is_theme() && (*it)->id() != current_theme) { |
| 371 remove_list.push_back((*it)->id()); |
| 372 } |
| 373 } |
| 374 for (size_t i = 0; i < remove_list.size(); ++i) |
| 375 service->UninstallExtension(remove_list[i], false, NULL); |
| 376 } |
| 377 |
351 void ThemeService::UseDefaultTheme() { | 378 void ThemeService::UseDefaultTheme() { |
352 ClearAllThemeData(); | 379 ClearAllThemeData(); |
353 NotifyThemeChanged(); | 380 NotifyThemeChanged(); |
354 content::RecordAction(UserMetricsAction("Themes_Reset")); | 381 content::RecordAction(UserMetricsAction("Themes_Reset")); |
355 } | 382 } |
356 | 383 |
357 void ThemeService::SetNativeTheme() { | 384 void ThemeService::SetNativeTheme() { |
358 UseDefaultTheme(); | 385 UseDefaultTheme(); |
359 } | 386 } |
360 | 387 |
361 bool ThemeService::UsingDefaultTheme() const { | 388 bool ThemeService::UsingDefaultTheme() const { |
362 std::string id = GetThemeID(); | 389 std::string id = GetThemeID(); |
363 return id == ThemeService::kDefaultThemeID || | 390 return id == ThemeService::kDefaultThemeID || |
364 id == kDefaultThemeGalleryID; | 391 id == kDefaultThemeGalleryID; |
365 } | 392 } |
366 | 393 |
367 bool ThemeService::UsingNativeTheme() const { | 394 bool ThemeService::UsingNativeTheme() const { |
368 return UsingDefaultTheme(); | 395 return UsingDefaultTheme(); |
369 } | 396 } |
370 | 397 |
371 void ThemeService::OnInfobarDisplayed() { | 398 std::string ThemeService::GetThemeID() const { |
372 number_of_infobars_++; | 399 return profile_->GetPrefs()->GetString(prefs::kCurrentThemeID); |
373 } | |
374 | |
375 void ThemeService::OnInfobarDestroyed() { | |
376 number_of_infobars_--; | |
377 | |
378 if (number_of_infobars_ == 0) | |
379 RemoveUnusedThemesForProfile(profile_); | |
380 } | 400 } |
381 | 401 |
382 // static | 402 // static |
383 std::string ThemeService::GetThemeIDForProfile(Profile* profile) { | |
384 return profile->GetPrefs()->GetString(prefs::kCurrentThemeID); | |
385 } | |
386 | |
387 // static | |
388 void ThemeService::SaveThemeIDForProfile( | |
389 Profile* profile, | |
390 const std::string& id) { | |
391 profile->GetPrefs()->SetString(prefs::kCurrentThemeID, id); | |
392 } | |
393 | |
394 // static | |
395 void ThemeService::RemoveUnusedThemesForProfile(Profile* profile) { | |
396 ExtensionService* extension_service = | |
397 extensions::ExtensionSystem::Get(profile)->extension_service(); | |
398 if (!extension_service) | |
399 return; | |
400 std::string current_theme = GetThemeIDForProfile(profile); | |
401 std::vector<std::string> remove_list; | |
402 const ExtensionSet* extensions = extension_service->extensions(); | |
403 for (ExtensionSet::const_iterator it = extensions->begin(); | |
404 it != extensions->end(); ++it) { | |
405 if ((*it)->is_theme() && (*it)->id() != current_theme) { | |
406 remove_list.push_back((*it)->id()); | |
407 } | |
408 } | |
409 for (size_t i = 0; i < remove_list.size(); ++i) | |
410 extension_service->UninstallExtension(remove_list[i], false, NULL); | |
411 } | |
412 | |
413 std::string ThemeService::GetThemeID() const { | |
414 return GetThemeIDForProfile(profile_); | |
415 } | |
416 | |
417 // static | |
418 std::string ThemeService::AlignmentToString(int alignment) { | 403 std::string ThemeService::AlignmentToString(int alignment) { |
419 // Convert from an AlignmentProperty back into a string. | 404 // Convert from an AlignmentProperty back into a string. |
420 std::string vertical_string(kAlignmentCenter); | 405 std::string vertical_string(kAlignmentCenter); |
421 std::string horizontal_string(kAlignmentCenter); | 406 std::string horizontal_string(kAlignmentCenter); |
422 | 407 |
423 if (alignment & ThemeService::ALIGN_TOP) | 408 if (alignment & ThemeService::ALIGN_TOP) |
424 vertical_string = kAlignmentTop; | 409 vertical_string = kAlignmentTop; |
425 else if (alignment & ThemeService::ALIGN_BOTTOM) | 410 else if (alignment & ThemeService::ALIGN_BOTTOM) |
426 vertical_string = kAlignmentBottom; | 411 vertical_string = kAlignmentBottom; |
427 | 412 |
(...skipping 171 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
599 | 584 |
600 return GetDefaultTint(id); | 585 return GetDefaultTint(id); |
601 } | 586 } |
602 | 587 |
603 void ThemeService::ClearAllThemeData() { | 588 void ThemeService::ClearAllThemeData() { |
604 // Clear our image cache. | 589 // Clear our image cache. |
605 FreePlatformCaches(); | 590 FreePlatformCaches(); |
606 theme_pack_ = NULL; | 591 theme_pack_ = NULL; |
607 | 592 |
608 profile_->GetPrefs()->ClearPref(prefs::kCurrentThemePackFilename); | 593 profile_->GetPrefs()->ClearPref(prefs::kCurrentThemePackFilename); |
609 SaveThemeIDForProfile(profile_, kDefaultThemeID); | 594 SaveThemeID(kDefaultThemeID); |
610 } | 595 } |
611 | 596 |
612 void ThemeService::LoadThemePrefs() { | 597 void ThemeService::LoadThemePrefs() { |
613 PrefService* prefs = profile_->GetPrefs(); | 598 PrefService* prefs = profile_->GetPrefs(); |
614 | 599 |
615 std::string current_id = GetThemeID(); | 600 std::string current_id = GetThemeID(); |
616 if (current_id != kDefaultThemeID) { | 601 if (current_id != kDefaultThemeID) { |
617 bool loaded_pack = false; | 602 bool loaded_pack = false; |
618 | 603 |
619 // If we don't have a file pack, we're updating from an old version. | 604 // If we don't have a file pack, we're updating from an old version. |
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
664 theme_syncable_service_->OnThemeChange(); | 649 theme_syncable_service_->OnThemeChange(); |
665 } | 650 } |
666 } | 651 } |
667 | 652 |
668 #if defined(OS_WIN) || defined(USE_AURA) | 653 #if defined(OS_WIN) || defined(USE_AURA) |
669 void ThemeService::FreePlatformCaches() { | 654 void ThemeService::FreePlatformCaches() { |
670 // Views (Skia) has no platform image cache to clear. | 655 // Views (Skia) has no platform image cache to clear. |
671 } | 656 } |
672 #endif | 657 #endif |
673 | 658 |
| 659 void ThemeService::Observe(int type, |
| 660 const content::NotificationSource& source, |
| 661 const content::NotificationDetails& details) { |
| 662 DCHECK(type == chrome::NOTIFICATION_EXTENSION_LOADED); |
| 663 const Extension* extension = content::Details<const Extension>(details).ptr(); |
| 664 if (!extension->is_theme()) { |
| 665 return; |
| 666 } |
| 667 SetTheme(extension); |
| 668 } |
| 669 |
674 void ThemeService::SavePackName(const FilePath& pack_path) { | 670 void ThemeService::SavePackName(const FilePath& pack_path) { |
675 profile_->GetPrefs()->SetFilePath( | 671 profile_->GetPrefs()->SetFilePath( |
676 prefs::kCurrentThemePackFilename, pack_path); | 672 prefs::kCurrentThemePackFilename, pack_path); |
677 } | 673 } |
678 | 674 |
| 675 void ThemeService::SaveThemeID(const std::string& id) { |
| 676 profile_->GetPrefs()->SetString(prefs::kCurrentThemeID, id); |
| 677 } |
| 678 |
679 void ThemeService::BuildFromExtension(const Extension* extension) { | 679 void ThemeService::BuildFromExtension(const Extension* extension) { |
680 scoped_refptr<BrowserThemePack> pack( | 680 scoped_refptr<BrowserThemePack> pack( |
681 BrowserThemePack::BuildFromExtension(extension)); | 681 BrowserThemePack::BuildFromExtension(extension)); |
682 if (!pack.get()) { | 682 if (!pack.get()) { |
683 // TODO(erg): We've failed to install the theme; perhaps we should tell the | 683 // TODO(erg): We've failed to install the theme; perhaps we should tell the |
684 // user? http://crbug.com/34780 | 684 // user? http://crbug.com/34780 |
685 LOG(ERROR) << "Could not load theme."; | 685 LOG(ERROR) << "Could not load theme."; |
686 return; | 686 return; |
687 } | 687 } |
688 | 688 |
689 ExtensionService* service = | 689 ExtensionService* service = |
690 extensions::ExtensionSystem::Get(profile_)->extension_service(); | 690 extensions::ExtensionSystem::Get(profile_)->extension_service(); |
691 if (!service) | 691 if (!service) |
692 return; | 692 return; |
693 | 693 |
694 // Write the packed file to disk. | 694 // Write the packed file to disk. |
695 FilePath pack_path = extension->path().Append(chrome::kThemePackFilename); | 695 FilePath pack_path = extension->path().Append(chrome::kThemePackFilename); |
696 service->GetFileTaskRunner()->PostTask( | 696 service->GetFileTaskRunner()->PostTask( |
697 FROM_HERE, | 697 FROM_HERE, |
698 base::Bind(&WritePackToDiskCallback, pack, pack_path)); | 698 base::Bind(&WritePackToDiskCallback, pack, pack_path)); |
699 | 699 |
700 SavePackName(pack_path); | 700 SavePackName(pack_path); |
701 theme_pack_ = pack; | 701 theme_pack_ = pack; |
702 } | 702 } |
703 | 703 |
| 704 void ThemeService::OnInfobarDisplayed() { |
| 705 number_of_infobars_++; |
| 706 } |
| 707 |
| 708 void ThemeService::OnInfobarDestroyed() { |
| 709 number_of_infobars_--; |
| 710 |
| 711 if (number_of_infobars_ == 0) |
| 712 RemoveUnusedThemes(); |
| 713 } |
| 714 |
704 ThemeSyncableService* ThemeService::GetThemeSyncableService() const { | 715 ThemeSyncableService* ThemeService::GetThemeSyncableService() const { |
705 return theme_syncable_service_.get(); | 716 return theme_syncable_service_.get(); |
706 } | 717 } |
OLD | NEW |