Index: chrome/browser/browser_theme_provider.cc |
diff --git a/chrome/browser/browser_theme_provider.cc b/chrome/browser/browser_theme_provider.cc |
index aceedf13b24b007ed899ae102758690a78143241..daf7b680a36c3d75e6999fa02f2f56baa2e5e394 100644 |
--- a/chrome/browser/browser_theme_provider.cc |
+++ b/chrome/browser/browser_theme_provider.cc |
@@ -13,6 +13,7 @@ |
#include "base/values.h" |
#include "chrome/browser/browser_list.h" |
#include "chrome/browser/browser_process.h" |
+#include "chrome/browser/browser_theme_pack.h" |
#include "chrome/browser/browser_window.h" |
#include "chrome/browser/extensions/extensions_service.h" |
#include "chrome/browser/metrics/user_metrics.h" |
@@ -36,50 +37,6 @@ |
#include "app/win_util.h" |
#endif |
-// Strings used by themes to identify colors for different parts of our UI. |
-const char* BrowserThemeProvider::kColorFrame = "frame"; |
-const char* BrowserThemeProvider::kColorFrameInactive = "frame_inactive"; |
-const char* BrowserThemeProvider::kColorFrameIncognito = "frame_incognito"; |
-const char* BrowserThemeProvider::kColorFrameIncognitoInactive = |
- "frame_incognito_inactive"; |
-const char* BrowserThemeProvider::kColorToolbar = "toolbar"; |
-const char* BrowserThemeProvider::kColorTabText = "tab_text"; |
-const char* BrowserThemeProvider::kColorBackgroundTabText = |
- "tab_background_text"; |
-const char* BrowserThemeProvider::kColorBookmarkText = "bookmark_text"; |
-const char* BrowserThemeProvider::kColorNTPBackground = "ntp_background"; |
-const char* BrowserThemeProvider::kColorNTPText = "ntp_text"; |
-const char* BrowserThemeProvider::kColorNTPLink = "ntp_link"; |
-const char* BrowserThemeProvider::kColorNTPLinkUnderline = "ntp_link_underline"; |
-const char* BrowserThemeProvider::kColorNTPHeader = "ntp_header"; |
-const char* BrowserThemeProvider::kColorNTPSection = "ntp_section"; |
-const char* BrowserThemeProvider::kColorNTPSectionText = "ntp_section_text"; |
-const char* BrowserThemeProvider::kColorNTPSectionLink = "ntp_section_link"; |
-const char* BrowserThemeProvider::kColorNTPSectionLinkUnderline = |
- "ntp_section_link_underline"; |
-const char* BrowserThemeProvider::kColorControlBackground = |
- "control_background"; |
-const char* BrowserThemeProvider::kColorButtonBackground = "button_background"; |
- |
-// Strings used by themes to identify tints to apply to different parts of |
-// our UI. The frame tints apply to the frame color and produce the |
-// COLOR_FRAME* colors. |
-const char* BrowserThemeProvider::kTintButtons = "buttons"; |
-const char* BrowserThemeProvider::kTintFrame = "frame"; |
-const char* BrowserThemeProvider::kTintFrameInactive = "frame_inactive"; |
-const char* BrowserThemeProvider::kTintFrameIncognito = "frame_incognito"; |
-const char* BrowserThemeProvider::kTintFrameIncognitoInactive = |
- "frame_incognito_inactive"; |
-const char* BrowserThemeProvider::kTintBackgroundTab = "background_tab"; |
- |
-// Strings used by themes to identify miscellaneous numerical properties. |
-const char* BrowserThemeProvider::kDisplayPropertyNTPAlignment = |
- "ntp_background_alignment"; |
-const char* BrowserThemeProvider::kDisplayPropertyNTPTiling = |
- "ntp_background_repeat"; |
-const char* BrowserThemeProvider::kDisplayPropertyNTPInverseLogo = |
- "ntp_logo_alternate"; |
- |
// Strings used in alignment properties. |
const char* BrowserThemeProvider::kAlignmentTop = "top"; |
const char* BrowserThemeProvider::kAlignmentBottom = "bottom"; |
@@ -92,68 +49,52 @@ const char* BrowserThemeProvider::kTilingRepeatX = "repeat-x"; |
const char* BrowserThemeProvider::kTilingRepeatY = "repeat-y"; |
const char* BrowserThemeProvider::kTilingRepeat = "repeat"; |
+// Saved default values. |
+const char* BrowserThemeProvider::kDefaultThemeID = ""; |
+ |
+namespace { |
+ |
+SkColor TintForUnderline(SkColor input) { |
+ return SkColorSetA(input, SkColorGetA(input) / 3); |
+} |
+ |
// Default colors. |
-const SkColor BrowserThemeProvider::kDefaultColorFrame = |
- SkColorSetRGB(77, 139, 217); |
-const SkColor BrowserThemeProvider::kDefaultColorFrameInactive = |
- SkColorSetRGB(152, 188, 233); |
-const SkColor BrowserThemeProvider::kDefaultColorFrameIncognito = |
- SkColorSetRGB(83, 106, 139); |
-const SkColor BrowserThemeProvider::kDefaultColorFrameIncognitoInactive = |
+const SkColor kDefaultColorFrame = SkColorSetRGB(77, 139, 217); |
+const SkColor kDefaultColorFrameInactive = SkColorSetRGB(152, 188, 233); |
+const SkColor kDefaultColorFrameIncognito = SkColorSetRGB(83, 106, 139); |
+const SkColor kDefaultColorFrameIncognitoInactive = |
SkColorSetRGB(126, 139, 156); |
-const SkColor BrowserThemeProvider::kDefaultColorToolbar = |
- SkColorSetRGB(210, 225, 246); |
-const SkColor BrowserThemeProvider::kDefaultColorTabText = SK_ColorBLACK; |
-const SkColor BrowserThemeProvider::kDefaultColorBackgroundTabText = |
- SkColorSetRGB(64, 64, 64); |
-const SkColor BrowserThemeProvider::kDefaultColorBookmarkText = |
- SkColorSetRGB(18, 50, 114); |
+const SkColor kDefaultColorToolbar = SkColorSetRGB(210, 225, 246); |
+const SkColor kDefaultColorTabText = SK_ColorBLACK; |
+const SkColor kDefaultColorBackgroundTabText = SkColorSetRGB(64, 64, 64); |
+const SkColor kDefaultColorBookmarkText = SkColorSetRGB(18, 50, 114); |
#if defined(OS_WIN) |
-const SkColor BrowserThemeProvider::kDefaultColorNTPBackground = |
+const SkColor kDefaultColorNTPBackground = |
color_utils::GetSysSkColor(COLOR_WINDOW); |
-const SkColor BrowserThemeProvider::kDefaultColorNTPText = |
+const SkColor kDefaultColorNTPText = |
color_utils::GetSysSkColor(COLOR_WINDOWTEXT); |
-const SkColor BrowserThemeProvider::kDefaultColorNTPLink = |
+const SkColor kDefaultColorNTPLink = |
color_utils::GetSysSkColor(COLOR_HOTLIGHT); |
#else |
// TODO(beng): source from theme provider. |
-const SkColor BrowserThemeProvider::kDefaultColorNTPBackground = SK_ColorWHITE; |
-const SkColor BrowserThemeProvider::kDefaultColorNTPText = SK_ColorBLACK; |
-const SkColor BrowserThemeProvider::kDefaultColorNTPLink = |
- SkColorSetRGB(6, 55, 116); |
+const SkColor kDefaultColorNTPBackground = SK_ColorWHITE; |
+const SkColor kDefaultColorNTPText = SK_ColorBLACK; |
+const SkColor kDefaultColorNTPLink = SkColorSetRGB(6, 55, 116); |
#endif |
-const SkColor BrowserThemeProvider::kDefaultColorNTPHeader = |
- SkColorSetRGB(75, 140, 220); |
-const SkColor BrowserThemeProvider::kDefaultColorNTPSection = |
- SkColorSetRGB(229, 239, 254); |
-const SkColor BrowserThemeProvider::kDefaultColorNTPSectionText = SK_ColorBLACK; |
-const SkColor BrowserThemeProvider::kDefaultColorNTPSectionLink = |
- SkColorSetRGB(6, 55, 116); |
-const SkColor BrowserThemeProvider::kDefaultColorControlBackground = |
- SkColorSetARGB(0, 0, 0, 0); |
-const SkColor BrowserThemeProvider::kDefaultColorButtonBackground = |
- SkColorSetARGB(0, 0, 0, 0); |
+const SkColor kDefaultColorNTPHeader = SkColorSetRGB(75, 140, 220); |
+const SkColor kDefaultColorNTPSection = SkColorSetRGB(229, 239, 254); |
+const SkColor kDefaultColorNTPSectionText = SK_ColorBLACK; |
+const SkColor kDefaultColorNTPSectionLink = SkColorSetRGB(6, 55, 116); |
+const SkColor kDefaultColorControlBackground = SkColorSetARGB(0, 0, 0, 0); |
+const SkColor kDefaultColorButtonBackground = SkColorSetARGB(0, 0, 0, 0); |
// Default tints. |
-const color_utils::HSL BrowserThemeProvider::kDefaultTintButtons = |
- { -1, -1, -1 }; |
-const color_utils::HSL BrowserThemeProvider::kDefaultTintFrame = { -1, -1, -1 }; |
-const color_utils::HSL BrowserThemeProvider::kDefaultTintFrameInactive = |
- { -1, -1, 0.75f }; |
-const color_utils::HSL BrowserThemeProvider::kDefaultTintFrameIncognito = |
- { -1, 0.2f, 0.35f }; |
-const color_utils::HSL |
- BrowserThemeProvider::kDefaultTintFrameIncognitoInactive = |
- { -1, 0.3f, 0.6f }; |
-const color_utils::HSL BrowserThemeProvider::kDefaultTintBackgroundTab = |
- { -1, 0.5, 0.75 }; |
- |
-// Saved default values. |
-const char* BrowserThemeProvider::kDefaultThemeID = ""; |
- |
-Lock BrowserThemeProvider::themed_image_cache_lock_; |
- |
-namespace { |
+const color_utils::HSL kDefaultTintButtons = { -1, -1, -1 }; |
+const color_utils::HSL kDefaultTintFrame = { -1, -1, -1 }; |
+const color_utils::HSL kDefaultTintFrameInactive = { -1, -1, 0.75f }; |
+const color_utils::HSL kDefaultTintFrameIncognito = { -1, 0.2f, 0.35f }; |
+const color_utils::HSL kDefaultTintFrameIncognitoInactive = { -1, 0.3f, 0.6f }; |
+const color_utils::HSL kDefaultTintBackgroundTab = { -1, 0.5, 0.75 }; |
// Default display properties. |
const int kDefaultDisplayPropertyNTPAlignment = |
@@ -166,35 +107,6 @@ const int kDefaultDisplayPropertyNTPInverseLogo = 0; |
// OpaqueBrowserFrameView. |
const int kRestoredTabVerticalOffset = 15; |
-// The image resources that will be tinted by the 'button' tint value. |
-const int kToolbarButtonIDs[] = { |
- IDR_BACK, IDR_BACK_D, IDR_BACK_H, IDR_BACK_P, |
- IDR_FORWARD, IDR_FORWARD_D, IDR_FORWARD_H, IDR_FORWARD_P, |
- IDR_RELOAD, IDR_RELOAD_H, IDR_RELOAD_P, |
- IDR_HOME, IDR_HOME_H, IDR_HOME_P, |
- IDR_STAR, IDR_STAR_NOBORDER, IDR_STAR_NOBORDER_CENTER, IDR_STAR_D, IDR_STAR_H, |
- IDR_STAR_P, |
- IDR_STARRED, IDR_STARRED_NOBORDER, IDR_STARRED_NOBORDER_CENTER, IDR_STARRED_H, |
- IDR_STARRED_P, |
- IDR_GO, IDR_GO_NOBORDER, IDR_GO_NOBORDER_CENTER, IDR_GO_H, IDR_GO_P, |
- IDR_STOP, IDR_STOP_NOBORDER, IDR_STOP_NOBORDER_CENTER, IDR_STOP_H, IDR_STOP_P, |
- IDR_MENU_BOOKMARK, |
- IDR_MENU_PAGE, IDR_MENU_PAGE_RTL, |
- IDR_MENU_CHROME, IDR_MENU_CHROME_RTL, |
- IDR_MENU_DROPARROW, |
- IDR_THROBBER, IDR_THROBBER_WAITING, IDR_THROBBER_LIGHT, |
- IDR_LOCATIONBG |
-}; |
- |
-bool HasButtonImage(int toolbar_button_id) { |
- static std::map<int, bool> button_images; |
- if (button_images.empty()) { |
- for (size_t i = 0; i < arraysize(kToolbarButtonIDs); ++i) |
- button_images[kToolbarButtonIDs[i]] = true; |
- } |
- return button_images.count(toolbar_button_id) > 0; |
-} |
- |
// The image resources we will allow people to theme. |
const int kThemeableImages[] = { |
IDR_THEME_FRAME, |
@@ -222,49 +134,21 @@ bool HasThemeableImage(int themeable_image_id) { |
return themeable_images.count(themeable_image_id) > 0; |
} |
- |
-class WriteImagesToDiskTask : public Task { |
+// Writes the theme pack to disk on a separate thread. |
+class WritePackToDiskTask : public Task { |
public: |
- WriteImagesToDiskTask( |
- const BrowserThemeProvider::ImagesDiskCache& images_disk_cache, |
- const BrowserThemeProvider::ImageCache& themed_image_cache) : |
- images_disk_cache_(images_disk_cache), |
- themed_image_cache_(themed_image_cache) { |
- } |
+ WritePackToDiskTask(BrowserThemePack* pack, const FilePath& path) |
+ : theme_pack_(pack), pack_path_(path) {} |
virtual void Run() { |
- AutoLock lock(BrowserThemeProvider::themed_image_cache_lock_); |
- for (BrowserThemeProvider::ImagesDiskCache::const_iterator iter( |
- images_disk_cache_.begin()); iter != images_disk_cache_.end(); |
- ++iter) { |
- FilePath image_path = iter->first; |
- BrowserThemeProvider::ImageCache::const_iterator themed_iter = |
- themed_image_cache_.find(iter->second); |
- if (themed_iter != themed_image_cache_.end()) { |
- SkBitmap* bitmap = themed_iter->second; |
- std::vector<unsigned char> image_data; |
- if (!gfx::PNGCodec::EncodeBGRASkBitmap(*bitmap, false, &image_data)) { |
- NOTREACHED() << "Image file could not be encoded."; |
- return; |
- } |
- const char* image_data_ptr = |
- reinterpret_cast<const char*>(&image_data[0]); |
- if (!file_util::WriteFile(image_path, |
- image_data_ptr, image_data.size())) { |
- NOTREACHED() << "Image file could not be written to disk."; |
- return; |
- } |
- } else { |
- NOTREACHED() << "Themed image missing from cache."; |
- return; |
- } |
+ if (!theme_pack_->WriteToDisk(pack_path_)) { |
+ NOTREACHED() << "Could not write theme pack to disk"; |
} |
} |
private: |
- // References to data held in the BrowserThemeProvider. |
- const BrowserThemeProvider::ImagesDiskCache& images_disk_cache_; |
- const BrowserThemeProvider::ImageCache& themed_image_cache_; |
+ scoped_refptr<BrowserThemePack> theme_pack_; |
+ FilePath pack_path_; |
}; |
} // namespace |
@@ -275,32 +159,13 @@ bool BrowserThemeProvider::IsThemeableImage(int resource_id) { |
BrowserThemeProvider::BrowserThemeProvider() |
: rb_(ResourceBundle::GetSharedInstance()), |
- profile_(NULL), |
- process_images_(false) { |
+ profile_(NULL) { |
// Initialize the themeable image map so we can use it on other threads. |
HasThemeableImage(0); |
- resource_names_[IDR_THEME_FRAME] = "theme_frame"; |
- resource_names_[IDR_THEME_FRAME_INACTIVE] = "theme_frame_inactive"; |
- resource_names_[IDR_THEME_FRAME_OVERLAY] = "theme_frame_overlay"; |
- resource_names_[IDR_THEME_FRAME_OVERLAY_INACTIVE] = |
- "theme_frame_overlay_inactive"; |
- resource_names_[IDR_THEME_FRAME_INCOGNITO] = "theme_frame_incognito"; |
- resource_names_[IDR_THEME_FRAME_INCOGNITO_INACTIVE] = |
- "theme_frame_incognito_inactive"; |
- resource_names_[IDR_THEME_TAB_BACKGROUND] = "theme_tab_background"; |
- resource_names_[IDR_THEME_TAB_BACKGROUND_INCOGNITO] = |
- "theme_tab_background_incognito"; |
- resource_names_[IDR_THEME_TOOLBAR] = "theme_toolbar"; |
- resource_names_[IDR_THEME_TAB_BACKGROUND_V] = "theme_tab_background_v"; |
- resource_names_[IDR_THEME_NTP_BACKGROUND] = "theme_ntp_background"; |
- resource_names_[IDR_THEME_BUTTON_BACKGROUND] = "theme_button_background"; |
- resource_names_[IDR_THEME_NTP_ATTRIBUTION] = "theme_ntp_attribution"; |
- resource_names_[IDR_THEME_WINDOW_CONTROL_BACKGROUND] = |
- "theme_window_control_background"; |
} |
BrowserThemeProvider::~BrowserThemeProvider() { |
- ClearCaches(); |
+ FreePlatformCaches(); |
RemoveUnusedThemes(); |
} |
@@ -309,121 +174,38 @@ void BrowserThemeProvider::Init(Profile* profile) { |
DCHECK(CalledOnValidThread()); |
profile_ = profile; |
- image_dir_ = profile_->GetPath().Append(chrome::kThemeImagesDirname); |
- if (!file_util::PathExists(image_dir_)) |
- file_util::CreateDirectory(image_dir_); |
- |
LoadThemePrefs(); |
} |
SkBitmap* BrowserThemeProvider::GetBitmapNamed(int id) const { |
DCHECK(CalledOnValidThread()); |
- // First check to see if the Skia image is in the themed cache. The themed |
- // cache is not changed in this method, so it can remain unlocked. |
- ImageCache::const_iterator themed_iter = themed_image_cache_.find(id); |
- if (themed_iter != themed_image_cache_.end()) |
- return themed_iter->second; |
- |
- // If Skia image is not in themed cache, check regular cache, and possibly |
- // generate and store. |
- ImageCache::const_iterator image_iter = image_cache_.find(id); |
- if (image_iter != image_cache_.end()) |
- return image_iter->second; |
- |
- scoped_ptr<SkBitmap> result; |
- |
- // Try to load the image from the extension. |
- result.reset(LoadThemeBitmap(id)); |
- |
- // If we still don't have an image, load it from resourcebundle. |
- if (!result.get()) |
- result.reset(new SkBitmap(*rb_.GetBitmapNamed(id))); |
- |
- if (result.get()) { |
- // If the requested image is part of the toolbar button set, and we have |
- // a provided tint for that set, tint it appropriately. |
- if (HasButtonImage(id) && tints_.count(kTintButtons)) { |
- SkBitmap* tinted = |
- new SkBitmap(TintBitmap(*result.release(), TINT_BUTTONS)); |
- result.reset(tinted); |
- } |
+ SkBitmap* bitmap = NULL; |
- // We loaded successfully. Cache the bitmap. |
- image_cache_[id] = result.get(); |
- return result.release(); |
- } else { |
- NOTREACHED() << "Failed to load a requested image"; |
- return NULL; |
- } |
+ if (theme_pack_.get()) |
+ bitmap = theme_pack_->GetBitmapNamed(id); |
+ |
+ if (!bitmap) |
+ bitmap = rb_.GetBitmapNamed(id); |
+ |
+ return bitmap; |
} |
SkColor BrowserThemeProvider::GetColor(int id) const { |
DCHECK(CalledOnValidThread()); |
- // Special-case NTP header - if the color isn't provided, we fall back to |
- // the section color. |
- if (id == COLOR_NTP_HEADER) { |
- ColorMap::const_iterator color_iter = colors_.find(kColorNTPHeader); |
- if (color_iter != colors_.end()) |
- return color_iter->second; |
- color_iter = colors_.find(kColorNTPSection); |
- return (color_iter == colors_.end()) ? |
- GetDefaultColor(id) : color_iter->second; |
- } |
- |
- // Special case the underline colors to use semi transparent in case not |
- // defined. |
- if (id == COLOR_NTP_SECTION_LINK_UNDERLINE) { |
- ColorMap::const_iterator color_iter = |
- colors_.find(kColorNTPSectionLinkUnderline); |
- if (color_iter != colors_.end()) |
- return color_iter->second; |
- SkColor color_section_link = GetColor(COLOR_NTP_SECTION_LINK); |
- return SkColorSetA(color_section_link, SkColorGetA(color_section_link) / 3); |
- } |
- |
- if (id == COLOR_NTP_LINK_UNDERLINE) { |
- ColorMap::const_iterator color_iter = colors_.find(kColorNTPLinkUnderline); |
- if (color_iter != colors_.end()) |
- return color_iter->second; |
- SkColor color_link = GetColor(COLOR_NTP_LINK); |
- return SkColorSetA(color_link, SkColorGetA(color_link) / 3); |
- } |
+ SkColor color; |
+ if (theme_pack_.get() && theme_pack_->GetColor(id, &color)) |
+ return color; |
- // TODO(glen): Figure out if we need to tint these. http://crbug.com/11578 |
- ColorMap::const_iterator color_iter = colors_.find(GetColorKey(id)); |
- return (color_iter == colors_.end()) ? |
- GetDefaultColor(id) : color_iter->second; |
+ return GetDefaultColor(id); |
} |
bool BrowserThemeProvider::GetDisplayProperty(int id, int* result) const { |
- switch (id) { |
- case NTP_BACKGROUND_ALIGNMENT: { |
- DisplayPropertyMap::const_iterator display_iter = |
- display_properties_.find(kDisplayPropertyNTPAlignment); |
- *result = (display_iter == display_properties_.end()) ? |
- kDefaultDisplayPropertyNTPAlignment : display_iter->second; |
- return true; |
- } |
- case NTP_BACKGROUND_TILING: { |
- DisplayPropertyMap::const_iterator display_iter = |
- display_properties_.find(kDisplayPropertyNTPTiling); |
- *result = (display_iter == display_properties_.end()) ? |
- kDefaultDisplayPropertyNTPTiling : display_iter->second; |
- return true; |
- } |
- case NTP_LOGO_ALTERNATE: { |
- DisplayPropertyMap::const_iterator display_iter = |
- display_properties_.find(kDisplayPropertyNTPInverseLogo); |
- *result = (display_iter == display_properties_.end()) ? |
- kDefaultDisplayPropertyNTPInverseLogo : display_iter->second; |
- return true; |
- } |
- default: |
- NOTREACHED() << "Unknown property requested"; |
- } |
- return false; |
+ if (theme_pack_.get()) |
+ return theme_pack_->GetDisplayProperty(id, result); |
+ |
+ return GetDefaultDisplayProperty(id, result); |
} |
bool BrowserThemeProvider::ShouldUseNativeFrame() const { |
@@ -440,15 +222,10 @@ bool BrowserThemeProvider::HasCustomImage(int id) const { |
if (!HasThemeableImage(id)) |
return false; |
- // A custom image = base name is NOT equal to resource name. See note in |
- // SaveThemeBitmap describing the process by which an original image is |
- // tagged. |
- ImageMap::const_iterator images_iter = images_.find(id); |
- ResourceNameMap::const_iterator names_iter = resource_names_.find(id); |
- if ((images_iter == images_.end()) || (names_iter == resource_names_.end())) |
- return false; |
- return !EndsWith(UTF8ToWide(images_iter->second), |
- UTF8ToWide(names_iter->second), false); |
+ if (theme_pack_) |
+ return theme_pack_->HasCustomImage(id); |
+ |
+ return false; |
} |
RefCountedMemory* BrowserThemeProvider::GetRawData(int id) const { |
@@ -458,57 +235,25 @@ RefCountedMemory* BrowserThemeProvider::GetRawData(int id) const { |
if (id == IDR_PRODUCT_LOGO && ntp_alternate != 0) |
id = IDR_PRODUCT_LOGO_WHITE; |
- RawDataMap::const_iterator data_iter = raw_data_.find(id); |
- if (data_iter != raw_data_.end()) |
- return data_iter->second; |
- |
- RefCountedMemory* data = ReadThemeFileData(id); |
+ RefCountedMemory* data = NULL; |
+ if (theme_pack_.get()) |
+ data = theme_pack_->GetRawData(id); |
if (!data) |
data = rb_.LoadDataResourceBytes(id); |
- if (!data) |
- return NULL; |
- raw_data_[id] = data; |
return data; |
} |
void BrowserThemeProvider::SetTheme(Extension* extension) { |
// Clear our image cache. |
- ClearCaches(); |
+ FreePlatformCaches(); |
DCHECK(extension); |
DCHECK(extension->IsTheme()); |
- SetImageData(extension->GetThemeImages(), |
- extension->path()); |
- SetColorData(extension->GetThemeColors()); |
- SetTintData(extension->GetThemeTints()); |
- |
- // Drop out to default theme if the theme data is empty. |
- if (images_.empty() && colors_.empty() && tints_.empty()) { |
- UseDefaultTheme(); |
- return; |
- } |
- |
- SetDisplayPropertyData(extension->GetThemeDisplayProperties()); |
- raw_data_.clear(); |
- SaveImageData(extension->GetThemeImages()); |
- SaveColorData(); |
- SaveTintData(); |
- SaveDisplayPropertyData(); |
+ BuildFromExtension(extension); |
SaveThemeID(extension->id()); |
- // Process all images when we first set theme. |
- process_images_ = true; |
- |
- GenerateFrameColors(); |
- if (ShouldTintFrames()) { |
- AutoLock lock(themed_image_cache_lock_); |
- GenerateFrameImages(); |
- GenerateTabImages(); |
- } |
- |
- WriteImagesToDisk(); |
NotifyThemeChanged(); |
UserMetrics::RecordAction("Themes_Installed", profile_); |
} |
@@ -543,36 +288,6 @@ std::string BrowserThemeProvider::GetThemeID() const { |
return WideToUTF8(id); |
} |
-RefCountedMemory* BrowserThemeProvider::ReadThemeFileData(int id) const { |
- ImageMap::const_iterator images_iter = images_.find(id); |
- if (images_iter != images_.end()) { |
- // First check to see if we have a registered theme extension and whether |
- // it can handle this resource. |
-#if defined(OS_WIN) |
- FilePath path = FilePath(UTF8ToWide(images_iter->second)); |
-#else |
- FilePath path = FilePath(images_iter->second); |
-#endif |
- if (!path.empty()) { |
- net::FileStream file; |
- int flags = base::PLATFORM_FILE_OPEN | base::PLATFORM_FILE_READ; |
- if (file.Open(path, flags) == net::OK) { |
- int64 avail = file.Available(); |
- if (avail > 0 && avail < INT_MAX) { |
- size_t size = static_cast<size_t>(avail); |
- std::vector<unsigned char> raw_data; |
- raw_data.resize(size); |
- char* data = reinterpret_cast<char*>(&(raw_data.front())); |
- if (file.ReadUntilComplete(data, size) == avail) |
- return RefCountedBytes::TakeVector(&raw_data); |
- } |
- } |
- } |
- } |
- |
- return NULL; |
-} |
- |
// static |
std::string BrowserThemeProvider::AlignmentToString(int alignment) { |
// Convert from an AlignmentProperty back into a string. |
@@ -646,313 +361,8 @@ int BrowserThemeProvider::StringToTiling(const std::string& tiling) { |
return BrowserThemeProvider::NO_REPEAT; |
} |
-void BrowserThemeProvider::SetColor(const char* key, const SkColor& color) { |
- colors_[key] = color; |
-} |
- |
-void BrowserThemeProvider::SetTint(const char* key, |
- const color_utils::HSL& tint) { |
- tints_[key] = tint; |
-} |
- |
-color_utils::HSL BrowserThemeProvider::GetTint(int id) const { |
- DCHECK(CalledOnValidThread()); |
- |
- TintMap::const_iterator tint_iter = tints_.find(GetTintKey(id)); |
- return (tint_iter == tints_.end()) ? GetDefaultTint(id) : tint_iter->second; |
-} |
- |
-void BrowserThemeProvider::GenerateFrameColors() { |
- // Generate any secondary frame colors that weren't provided. |
- SkColor frame = GetColor(COLOR_FRAME); |
- |
- if (!colors_.count(kColorFrame)) |
- colors_[kColorFrame] = HSLShift(frame, GetTint(TINT_FRAME)); |
- if (!colors_.count(kColorFrameInactive)) { |
- colors_[kColorFrameInactive] = |
- HSLShift(frame, GetTint(TINT_FRAME_INACTIVE)); |
- } |
- if (!colors_.count(kColorFrameIncognito)) { |
- colors_[kColorFrameIncognito] = |
- HSLShift(frame, GetTint(TINT_FRAME_INCOGNITO)); |
- } |
- if (!colors_.count(kColorFrameIncognitoInactive)) { |
- colors_[kColorFrameIncognitoInactive] = |
- HSLShift(frame, GetTint(TINT_FRAME_INCOGNITO_INACTIVE)); |
- } |
-} |
- |
-void BrowserThemeProvider::GenerateFrameImages() const { |
- // A map of frame image IDs to the tints for those ids. |
- typedef std::map<int, int> FrameTintMap; |
- static FrameTintMap frame_tints; |
- if (frame_tints.empty()) { |
- frame_tints[IDR_THEME_FRAME] = TINT_FRAME; |
- frame_tints[IDR_THEME_FRAME_INACTIVE] = TINT_FRAME_INACTIVE; |
- frame_tints[IDR_THEME_FRAME_OVERLAY] = TINT_FRAME; |
- frame_tints[IDR_THEME_FRAME_OVERLAY_INACTIVE] = TINT_FRAME_INACTIVE; |
- frame_tints[IDR_THEME_FRAME_INCOGNITO] = TINT_FRAME_INCOGNITO; |
- frame_tints[IDR_THEME_FRAME_INCOGNITO_INACTIVE] = |
- TINT_FRAME_INCOGNITO_INACTIVE; |
- } |
- |
- for (FrameTintMap::const_iterator iter(frame_tints.begin()); |
- iter != frame_tints.end(); ++iter) { |
- int id = iter->first; |
- scoped_ptr<SkBitmap> frame; |
- // If there's no frame image provided for the specified id, then load |
- // the default provided frame. If that's not provided, skip this whole |
- // thing and just use the default images. |
- int base_id; |
- std::string resource_name; |
- |
- // If we've already processed the images for this theme, they're all |
- // waiting on disk -- just load them in. |
- if (!process_images_) { |
- frame.reset(LoadThemeBitmap(id)); |
- if (frame.get()) |
- themed_image_cache_[id] = new SkBitmap(*frame.get()); |
- } else { |
- resource_name = resource_names_.find(id)->second; |
- if (id == IDR_THEME_FRAME_INCOGNITO_INACTIVE) { |
- base_id = HasCustomImage(IDR_THEME_FRAME_INCOGNITO) ? |
- IDR_THEME_FRAME_INCOGNITO : IDR_THEME_FRAME; |
- } else if (id == IDR_THEME_FRAME_OVERLAY_INACTIVE) { |
- base_id = IDR_THEME_FRAME_OVERLAY; |
- } else if (id == IDR_THEME_FRAME_INACTIVE) { |
- base_id = IDR_THEME_FRAME; |
- } else if (id == IDR_THEME_FRAME_INCOGNITO && |
- !HasCustomImage(IDR_THEME_FRAME_INCOGNITO)) { |
- base_id = IDR_THEME_FRAME; |
- } else { |
- base_id = id; |
- } |
- |
- if (HasCustomImage(id)) { |
- frame.reset(LoadThemeBitmap(id)); |
- } else if (base_id != id && HasCustomImage(base_id)) { |
- frame.reset(LoadThemeBitmap(base_id)); |
- } else if (base_id == IDR_THEME_FRAME_OVERLAY && |
- HasCustomImage(IDR_THEME_FRAME)) { |
- // If there is no theme overlay, don't tint the default frame, |
- // because it will overwrite the custom frame image when we cache and |
- // reload from disk. |
- frame.reset(NULL); |
- } else { |
- // If the theme doesn't specify an image, then apply the tint to |
- // the default frame. |
- frame.reset(new SkBitmap(*rb_.GetBitmapNamed(IDR_THEME_FRAME))); |
- } |
- |
- if (frame.get()) { |
- SkBitmap* tinted = new SkBitmap(TintBitmap(*frame, iter->second)); |
- themed_image_cache_[id] = tinted; |
- SaveThemeBitmap(resource_name, id); |
- } |
- } |
- } |
-} |
- |
-void BrowserThemeProvider::GenerateTabImages() const { |
- GenerateTabBackgroundBitmap(IDR_THEME_TAB_BACKGROUND); |
- GenerateTabBackgroundBitmap(IDR_THEME_TAB_BACKGROUND_INCOGNITO); |
-} |
- |
-void BrowserThemeProvider::ClearAllThemeData() { |
- // Clear our image cache. |
- ClearCaches(); |
- |
- images_.clear(); |
- colors_.clear(); |
- tints_.clear(); |
- display_properties_.clear(); |
- raw_data_.clear(); |
- |
- SaveImageData(NULL); |
- SaveColorData(); |
- SaveTintData(); |
- SaveDisplayPropertyData(); |
- SaveThemeID(kDefaultThemeID); |
-} |
- |
-void BrowserThemeProvider::LoadThemePrefs() { |
- process_images_ = false; |
- PrefService* prefs = profile_->GetPrefs(); |
- |
- // TODO(glen): Figure out if any custom prefs were loaded, and if so UMA-log |
- // the fact that a theme was loaded. |
- if (!prefs->HasPrefPath(prefs::kCurrentThemeImages) && |
- !prefs->HasPrefPath(prefs::kCurrentThemeColors) && |
- !prefs->HasPrefPath(prefs::kCurrentThemeTints)) |
- return; |
- |
- // Our prefs already have the extension path baked in, so we don't need to |
- // provide it. |
- SetImageData(prefs->GetMutableDictionary(prefs::kCurrentThemeImages), |
- FilePath()); |
- SetColorData(prefs->GetMutableDictionary(prefs::kCurrentThemeColors)); |
- SetTintData(prefs->GetMutableDictionary(prefs::kCurrentThemeTints)); |
- SetDisplayPropertyData( |
- prefs->GetMutableDictionary(prefs::kCurrentThemeDisplayProperties)); |
- |
- // If we're not loading the frame from the cached image dir, we are using an |
- // old preferences file, or the processed images were not saved correctly. |
- // Force image reprocessing and caching. |
- ImageMap::const_iterator images_iter = images_.find(IDR_THEME_FRAME); |
- if (images_iter != images_.end()) { |
-#if defined(OS_WIN) |
- FilePath cache_path = FilePath(UTF8ToWide(images_iter->second)); |
-#else |
- FilePath cache_path = FilePath(images_iter->second); |
-#endif |
- process_images_ = !file_util::ContainsPath(image_dir_, cache_path); |
- } |
- |
- GenerateFrameColors(); |
- // Scope for AutoLock on themed_image_cache. |
- { |
- AutoLock lock(themed_image_cache_lock_); |
- GenerateFrameImages(); |
- GenerateTabImages(); |
- } |
- |
- if (process_images_) { |
- WriteImagesToDisk(); |
- UserMetrics::RecordAction("Migrated noncached to cached theme.", profile_); |
- } |
- UserMetrics::RecordAction("Themes_loaded", profile_); |
-} |
- |
-void BrowserThemeProvider::NotifyThemeChanged() { |
- // Redraw! |
- NotificationService* service = NotificationService::current(); |
- service->Notify(NotificationType::BROWSER_THEME_CHANGED, |
- Source<BrowserThemeProvider>(this), |
- NotificationService::NoDetails()); |
-} |
- |
-SkBitmap* BrowserThemeProvider::LoadThemeBitmap(int id) const { |
- DCHECK(CalledOnValidThread()); |
- |
- if (!HasThemeableImage(id)) |
- return NULL; |
- |
- scoped_refptr<RefCountedMemory> raw_data; |
- |
- // We special case images related to the NTP so we first try raw data. Why? |
- // Because the DOMUI stuff uses that interface to return raw PNG data instead |
- // of the normal theme interface which returns SkBitmaps. GetRawData() also |
- // caches the PNG data so it opens new tab pages faster. If we didn't try and |
- // otherwise we would be loading big images twice, once through GetRawData() |
- // and once here. Ouch. So either we prime the GetRawData() cache for when |
- // DOMUIThemeSource requests our image, or we take advantage of the already |
- // loaded data, saving a trip to disk. |
- if (id == IDR_THEME_NTP_BACKGROUND) |
- raw_data = GetRawData(id); |
- |
- if (!raw_data) |
- raw_data = ReadThemeFileData(id); |
- |
- if (raw_data) { |
- // Decode the PNG. |
- SkBitmap bitmap; |
- if (!gfx::PNGCodec::Decode(raw_data->front(), raw_data->size(), |
- &bitmap)) { |
- NOTREACHED() << "Unable to decode theme image resource " << id; |
- return NULL; |
- } |
- |
- return new SkBitmap(bitmap); |
- } else { |
- // TODO(glen): File no-longer exists, we're out of date. We should |
- // clear the theme (or maybe just the pref that points to this |
- // image). |
- return NULL; |
- } |
-} |
- |
-void BrowserThemeProvider::SaveThemeBitmap(std::string resource_name, |
- int id) const { |
- DCHECK(CalledOnValidThread()); |
- if (!themed_image_cache_.count(id)) { |
- NOTREACHED(); |
- return; |
- } |
- |
- // The images_ directory, at this point, contains only the custom images |
- // provided by the extension. We tag these images "_original" in the prefs |
- // file so we can distinguish them from images which have been generated and |
- // saved to disk by the theme caching process (WriteImagesToDisk). This way, |
- // when we call HasCustomImage, we can check for the "_original" tag to see |
- // whether an image was originally provided by the extension, or saved |
- // in the caching process. |
- if (images_.count(id)) |
- resource_name.append("_original"); |
- |
-#if defined(OS_WIN) |
- FilePath image_path = image_dir_.Append(UTF8ToWide(resource_name)); |
-#elif defined(OS_POSIX) |
- FilePath image_path = image_dir_.Append(resource_name); |
-#endif |
- |
- images_disk_cache_[image_path] = id; |
-} |
- |
-#if defined(OS_WIN) |
-void BrowserThemeProvider::FreePlatformCaches() { |
- // Views (Skia) has no platform image cache to clear. |
-} |
-#endif |
- |
-SkBitmap* BrowserThemeProvider::GenerateTabBackgroundBitmapImpl(int id) const { |
- int base_id = (id == IDR_THEME_TAB_BACKGROUND) ? |
- IDR_THEME_FRAME : IDR_THEME_FRAME_INCOGNITO; |
- // According to Miranda, it is safe to read from the themed_image_cache_ here |
- // because we only lock to write on the UI thread, and we only lock to read |
- // on the cache writing thread. |
- ImageCache::const_iterator themed_iter = themed_image_cache_.find(base_id); |
- if (themed_iter == themed_image_cache_.end()) |
- return NULL; |
- |
- SkBitmap bg_tint = TintBitmap(*(themed_iter->second), TINT_BACKGROUND_TAB); |
- int vertical_offset = HasCustomImage(id) ? kRestoredTabVerticalOffset : 0; |
- SkBitmap* bg_tab = new SkBitmap(SkBitmapOperations::CreateTiledBitmap( |
- bg_tint, 0, vertical_offset, bg_tint.width(), bg_tint.height())); |
- |
- // If they've provided a custom image, overlay it. |
- if (HasCustomImage(id)) { |
- SkBitmap* overlay = LoadThemeBitmap(id); |
- if (overlay) { |
- SkCanvas canvas(*bg_tab); |
- for (int x = 0; x < bg_tab->width(); x += overlay->width()) |
- canvas.drawBitmap(*overlay, static_cast<SkScalar>(x), 0, NULL); |
- } |
- } |
- |
- return bg_tab; |
-} |
- |
-const std::string BrowserThemeProvider::GetTintKey(int id) const { |
- switch (id) { |
- case TINT_FRAME: |
- return kTintFrame; |
- case TINT_FRAME_INACTIVE: |
- return kTintFrameInactive; |
- case TINT_FRAME_INCOGNITO: |
- return kTintFrameIncognito; |
- case TINT_FRAME_INCOGNITO_INACTIVE: |
- return kTintFrameIncognitoInactive; |
- case TINT_BUTTONS: |
- return kTintButtons; |
- case TINT_BACKGROUND_TAB: |
- return kTintBackgroundTab; |
- default: |
- NOTREACHED() << "Unknown tint requested"; |
- return ""; |
- } |
-} |
- |
-color_utils::HSL BrowserThemeProvider::GetDefaultTint(int id) const { |
+// static |
+color_utils::HSL BrowserThemeProvider::GetDefaultTint(int id) { |
switch (id) { |
case TINT_FRAME: |
return kDefaultTintFrame; |
@@ -972,53 +382,8 @@ color_utils::HSL BrowserThemeProvider::GetDefaultTint(int id) const { |
} |
} |
-const std::string BrowserThemeProvider::GetColorKey(int id) const { |
- switch (id) { |
- case COLOR_FRAME: |
- return kColorFrame; |
- case COLOR_FRAME_INACTIVE: |
- return kColorFrameInactive; |
- case COLOR_FRAME_INCOGNITO: |
- return kColorFrameIncognito; |
- case COLOR_FRAME_INCOGNITO_INACTIVE: |
- return kColorFrameIncognitoInactive; |
- case COLOR_TOOLBAR: |
- return kColorToolbar; |
- case COLOR_TAB_TEXT: |
- return kColorTabText; |
- case COLOR_BACKGROUND_TAB_TEXT: |
- return kColorBackgroundTabText; |
- case COLOR_BOOKMARK_TEXT: |
- return kColorBookmarkText; |
- case COLOR_NTP_BACKGROUND: |
- return kColorNTPBackground; |
- case COLOR_NTP_TEXT: |
- return kColorNTPText; |
- case COLOR_NTP_LINK: |
- return kColorNTPLink; |
- case COLOR_NTP_LINK_UNDERLINE: |
- return kColorNTPLinkUnderline; |
- case COLOR_NTP_HEADER: |
- return kColorNTPHeader; |
- case COLOR_NTP_SECTION: |
- return kColorNTPSection; |
- case COLOR_NTP_SECTION_TEXT: |
- return kColorNTPSectionText; |
- case COLOR_NTP_SECTION_LINK: |
- return kColorNTPSectionLink; |
- case COLOR_NTP_SECTION_LINK_UNDERLINE: |
- return kColorNTPSectionLinkUnderline; |
- case COLOR_CONTROL_BACKGROUND: |
- return kColorControlBackground; |
- case COLOR_BUTTON_BACKGROUND: |
- return kColorButtonBackground; |
- default: |
- NOTREACHED() << "Unknown color requested"; |
- return ""; |
- } |
-} |
- |
-SkColor BrowserThemeProvider::GetDefaultColor(int id) const { |
+// static |
+SkColor BrowserThemeProvider::GetDefaultColor(int id) { |
switch (id) { |
case COLOR_FRAME: |
return kDefaultColorFrame; |
@@ -1042,6 +407,8 @@ SkColor BrowserThemeProvider::GetDefaultColor(int id) const { |
return kDefaultColorNTPText; |
case COLOR_NTP_LINK: |
return kDefaultColorNTPLink; |
+ case COLOR_NTP_LINK_UNDERLINE: |
+ return TintForUnderline(kDefaultColorNTPLink); |
case COLOR_NTP_HEADER: |
return kDefaultColorNTPHeader; |
case COLOR_NTP_SECTION: |
@@ -1050,6 +417,8 @@ SkColor BrowserThemeProvider::GetDefaultColor(int id) const { |
return kDefaultColorNTPSectionText; |
case COLOR_NTP_SECTION_LINK: |
return kDefaultColorNTPSectionLink; |
+ case COLOR_NTP_SECTION_LINK_UNDERLINE: |
+ return TintForUnderline(kDefaultColorNTPSectionLink); |
case COLOR_CONTROL_BACKGROUND: |
return kDefaultColorControlBackground; |
case COLOR_BUTTON_BACKGROUND: |
@@ -1060,289 +429,114 @@ SkColor BrowserThemeProvider::GetDefaultColor(int id) const { |
} |
} |
-SkBitmap BrowserThemeProvider::TintBitmap(const SkBitmap& bitmap, |
- int hsl_id) const { |
- return SkBitmapOperations::CreateHSLShiftedBitmap(bitmap, GetTint(hsl_id)); |
-} |
- |
-void BrowserThemeProvider::SetImageData(DictionaryValue* images_value, |
- FilePath images_path) { |
- images_.clear(); |
- |
- if (!images_value) |
- return; |
- |
- for (DictionaryValue::key_iterator iter(images_value->begin_keys()); |
- iter != images_value->end_keys(); ++iter) { |
- std::string val; |
- if (images_value->GetStringWithoutPathExpansion(*iter, &val)) { |
- int id = ThemeResourcesUtil::GetId(WideToUTF8(*iter)); |
- if (id != -1) { |
- if (!images_path.empty()) { |
- images_[id] = |
- WideToUTF8(images_path.AppendASCII(val).ToWStringHack()); |
- resource_names_[id] = WideToASCII(*iter); |
- } else { |
- images_[id] = val; |
- } |
- } |
- } |
+// static |
+bool BrowserThemeProvider::GetDefaultDisplayProperty(int id, int* result) { |
+ switch (id) { |
+ case NTP_BACKGROUND_ALIGNMENT: |
+ *result = kDefaultDisplayPropertyNTPAlignment; |
+ return true; |
+ case NTP_BACKGROUND_TILING: |
+ *result = kDefaultDisplayPropertyNTPTiling; |
+ return true; |
+ case NTP_LOGO_ALTERNATE: |
+ *result = kDefaultDisplayPropertyNTPInverseLogo; |
+ return true; |
} |
+ |
+ return false; |
} |
-void BrowserThemeProvider::SetColorData(DictionaryValue* colors_value) { |
- colors_.clear(); |
+color_utils::HSL BrowserThemeProvider::GetTint(int id) const { |
+ DCHECK(CalledOnValidThread()); |
- if (!colors_value) |
- return; |
+ color_utils::HSL hsl; |
+ if (theme_pack_.get() && theme_pack_->GetTint(id, &hsl)) |
+ return hsl; |
- for (DictionaryValue::key_iterator iter(colors_value->begin_keys()); |
- iter != colors_value->end_keys(); ++iter) { |
- ListValue* color_list; |
- if (colors_value->GetListWithoutPathExpansion(*iter, &color_list) && |
- ((color_list->GetSize() == 3) || (color_list->GetSize() == 4))) { |
- int r, g, b; |
- color_list->GetInteger(0, &r); |
- color_list->GetInteger(1, &g); |
- color_list->GetInteger(2, &b); |
- if (color_list->GetSize() == 4) { |
- double alpha; |
- int alpha_int; |
- if (color_list->GetReal(3, &alpha)) { |
- colors_[WideToUTF8(*iter)] = |
- SkColorSetARGB(static_cast<int>(alpha * 255), r, g, b); |
- } else if (color_list->GetInteger(3, &alpha_int) && |
- (alpha_int == 0 || alpha_int == 1)) { |
- colors_[WideToUTF8(*iter)] = |
- SkColorSetARGB(alpha_int ? 255 : 0, r, g, b); |
- } |
- } else { |
- colors_[WideToUTF8(*iter)] = SkColorSetRGB(r, g, b); |
- } |
- } |
- } |
+ return GetDefaultTint(id); |
} |
-void BrowserThemeProvider::SetTintData(DictionaryValue* tints_value) { |
- tints_.clear(); |
- |
- if (!tints_value) |
- return; |
+void BrowserThemeProvider::ClearAllThemeData() { |
+ // Clear our image cache. |
+ FreePlatformCaches(); |
+ theme_pack_ = NULL; |
- for (DictionaryValue::key_iterator iter(tints_value->begin_keys()); |
- iter != tints_value->end_keys(); ++iter) { |
- ListValue* tint_list; |
- if (tints_value->GetListWithoutPathExpansion(*iter, &tint_list) && |
- (tint_list->GetSize() == 3)) { |
- color_utils::HSL hsl = { -1, -1, -1 }; |
- int value = 0; |
- if (!tint_list->GetReal(0, &hsl.h) && tint_list->GetInteger(0, &value)) |
- hsl.h = value; |
- if (!tint_list->GetReal(1, &hsl.s) && tint_list->GetInteger(1, &value)) |
- hsl.s = value; |
- if (!tint_list->GetReal(2, &hsl.l) && tint_list->GetInteger(2, &value)) |
- hsl.l = value; |
- |
- tints_[WideToUTF8(*iter)] = hsl; |
- } |
- } |
+ profile_->GetPrefs()->ClearPref(prefs::kCurrentThemePackFilename); |
+ SaveThemeID(kDefaultThemeID); |
} |
-void BrowserThemeProvider::SetDisplayPropertyData( |
- DictionaryValue* display_properties_value) { |
- display_properties_.clear(); |
+void BrowserThemeProvider::LoadThemePrefs() { |
+ PrefService* prefs = profile_->GetPrefs(); |
- if (!display_properties_value) |
- return; |
+ std::string current_id = GetThemeID(); |
+ if (current_id != kDefaultThemeID) { |
+ bool loaded_pack = false; |
- for (DictionaryValue::key_iterator iter( |
- display_properties_value->begin_keys()); |
- iter != display_properties_value->end_keys(); ++iter) { |
- // New tab page alignment and background tiling. |
- if (base::strcasecmp(WideToUTF8(*iter).c_str(), |
- kDisplayPropertyNTPAlignment) == 0) { |
- std::string val; |
- if (display_properties_value->GetStringWithoutPathExpansion(*iter, |
- &val)) { |
- display_properties_[kDisplayPropertyNTPAlignment] = |
- StringToAlignment(val); |
- } |
- } else if (base::strcasecmp(WideToUTF8(*iter).c_str(), |
- kDisplayPropertyNTPTiling) == 0) { |
- std::string val; |
- if (display_properties_value->GetStringWithoutPathExpansion(*iter, &val)) |
- display_properties_[kDisplayPropertyNTPTiling] = StringToTiling(val); |
- } |
- if (base::strcasecmp(WideToUTF8(*iter).c_str(), |
- kDisplayPropertyNTPInverseLogo) == 0) { |
- int val = 0; |
- if (display_properties_value->GetIntegerWithoutPathExpansion(*iter, &val)) |
- display_properties_[kDisplayPropertyNTPInverseLogo] = val; |
+ // If we don't have a file pack, we're updating from an old version. |
+ FilePath path = prefs->GetFilePath(prefs::kCurrentThemePackFilename); |
+ if (path != FilePath()) { |
+ theme_pack_ = BrowserThemePack::BuildFromDataPack(path, current_id); |
+ loaded_pack = theme_pack_.get() != NULL; |
} |
- } |
-} |
-SkBitmap* BrowserThemeProvider::GenerateTabBackgroundBitmap(int id) const { |
- if (id == IDR_THEME_TAB_BACKGROUND || |
- id == IDR_THEME_TAB_BACKGROUND_INCOGNITO) { |
- // The requested image is a background tab. Get a frame to create the |
- // tab against. As themes don't use the glass frame, we don't have to |
- // worry about compositing them together, as our default theme provides |
- // the necessary bitmaps. |
- if (!process_images_) { |
- scoped_ptr<SkBitmap> frame; |
- frame.reset(LoadThemeBitmap(id)); |
- if (frame.get()) |
- themed_image_cache_[id] = new SkBitmap(*frame.get()); |
+ if (loaded_pack) { |
+ UserMetrics::RecordAction("Themes.Loaded", profile_); |
} else { |
- SkBitmap* bg_tab = GenerateTabBackgroundBitmapImpl(id); |
- |
- if (bg_tab) { |
- std::string resource_name((id == IDR_THEME_TAB_BACKGROUND) ? |
- "theme_tab_background" : "theme_tab_background_incognito"); |
- themed_image_cache_[id] = bg_tab; |
- SaveThemeBitmap(resource_name, id); |
- return bg_tab; |
- } |
- } |
- } |
- return NULL; |
-} |
- |
-void BrowserThemeProvider::SaveImageData(DictionaryValue* images_value) const { |
- // Save our images data. |
- DictionaryValue* pref_images = |
- profile_->GetPrefs()->GetMutableDictionary(prefs::kCurrentThemeImages); |
- pref_images->Clear(); |
- |
- if (!images_value) |
- return; |
- |
- for (DictionaryValue::key_iterator iter(images_value->begin_keys()); |
- iter != images_value->end_keys(); ++iter) { |
- std::string val; |
- if (images_value->GetStringWithoutPathExpansion(*iter, &val)) { |
- int id = ThemeResourcesUtil::GetId(WideToUTF8(*iter)); |
- if (id != -1) { |
- pref_images->SetWithoutPathExpansion(*iter, |
- Value::CreateStringValue(images_.find(id)->second)); |
+ // TODO(erg): We need to pop up a dialog informing the user that their |
+ // theme is being migrated. |
+ ExtensionsService* service = profile_->GetExtensionsService(); |
+ if (service) { |
+ Extension* extension = service->GetExtensionById(current_id, false); |
+ if (extension) { |
+ DLOG(ERROR) << "Migrating theme"; |
+ BuildFromExtension(extension); |
+ UserMetrics::RecordAction("Themes.Migrated", profile_); |
+ } else { |
+ DLOG(ERROR) << "Theme is mysteriously gone."; |
+ ClearAllThemeData(); |
+ UserMetrics::RecordAction("Themes.Gone", profile_); |
+ } |
} |
} |
} |
} |
-void BrowserThemeProvider::SaveColorData() const { |
- // Save our color data. |
- DictionaryValue* pref_colors = |
- profile_->GetPrefs()->GetMutableDictionary(prefs::kCurrentThemeColors); |
- pref_colors->Clear(); |
- |
- if (colors_.empty()) |
- return; |
- |
- for (ColorMap::const_iterator iter(colors_.begin()); iter != colors_.end(); |
- ++iter) { |
- SkColor rgba = iter->second; |
- ListValue* rgb_list = new ListValue(); |
- rgb_list->Set(0, Value::CreateIntegerValue(SkColorGetR(rgba))); |
- rgb_list->Set(1, Value::CreateIntegerValue(SkColorGetG(rgba))); |
- rgb_list->Set(2, Value::CreateIntegerValue(SkColorGetB(rgba))); |
- if (SkColorGetA(rgba) != 255) |
- rgb_list->Set(3, Value::CreateRealValue(SkColorGetA(rgba) / 255.0)); |
- pref_colors->Set(UTF8ToWide(iter->first), rgb_list); |
- } |
-} |
- |
-void BrowserThemeProvider::SaveTintData() const { |
- // Save our tint data. |
- DictionaryValue* pref_tints = |
- profile_->GetPrefs()->GetMutableDictionary(prefs::kCurrentThemeTints); |
- pref_tints->Clear(); |
- |
- if (tints_.empty()) |
- return; |
- |
- for (TintMap::const_iterator iter(tints_.begin()); iter != tints_.end(); |
- ++iter) { |
- color_utils::HSL hsl = iter->second; |
- ListValue* hsl_list = new ListValue(); |
- hsl_list->Set(0, Value::CreateRealValue(hsl.h)); |
- hsl_list->Set(1, Value::CreateRealValue(hsl.s)); |
- hsl_list->Set(2, Value::CreateRealValue(hsl.l)); |
- pref_tints->Set(UTF8ToWide(iter->first), hsl_list); |
- } |
+void BrowserThemeProvider::NotifyThemeChanged() { |
+ // Redraw! |
+ NotificationService* service = NotificationService::current(); |
+ service->Notify(NotificationType::BROWSER_THEME_CHANGED, |
+ Source<BrowserThemeProvider>(this), |
+ NotificationService::NoDetails()); |
} |
-void BrowserThemeProvider::SaveDisplayPropertyData() const { |
- // Save our display property data. |
- DictionaryValue* pref_display_properties = |
- profile_->GetPrefs()-> |
- GetMutableDictionary(prefs::kCurrentThemeDisplayProperties); |
- pref_display_properties->Clear(); |
- |
- if (display_properties_.empty()) |
- return; |
- |
- for (DisplayPropertyMap::const_iterator iter(display_properties_.begin()); |
- iter != display_properties_.end(); ++iter) { |
- if (base::strcasecmp(iter->first.c_str(), |
- kDisplayPropertyNTPAlignment) == 0) { |
- pref_display_properties->SetString(UTF8ToWide(iter->first), |
- AlignmentToString(iter->second)); |
- } else if (base::strcasecmp(iter->first.c_str(), |
- kDisplayPropertyNTPTiling) == 0) { |
- pref_display_properties->SetString(UTF8ToWide(iter->first), |
- TilingToString(iter->second)); |
- } |
- if (base::strcasecmp(iter->first.c_str(), |
- kDisplayPropertyNTPInverseLogo) == 0) { |
- pref_display_properties->SetInteger(UTF8ToWide(iter->first), |
- iter->second); |
- } |
- } |
+#if defined(OS_WIN) |
+void BrowserThemeProvider::FreePlatformCaches() { |
+ // Views (Skia) has no platform image cache to clear. |
} |
+#endif |
-void BrowserThemeProvider::SaveCachedImageData() const { |
- DictionaryValue* pref_images = |
- profile_->GetPrefs()->GetMutableDictionary(prefs::kCurrentThemeImages); |
- |
- for (ImagesDiskCache::const_iterator it(images_disk_cache_.begin()); |
- it != images_disk_cache_.end(); ++it) { |
- std::wstring disk_path = it->first.ToWStringHack(); |
- std::string pref_name = resource_names_.find(it->second)->second; |
- pref_images->SetString(UTF8ToWide(pref_name), WideToUTF8(disk_path)); |
- } |
- profile_->GetPrefs()->ScheduleSavePersistentPrefs(); |
+void BrowserThemeProvider::SavePackName(const FilePath& pack_path) { |
+ profile_->GetPrefs()->SetFilePath( |
+ prefs::kCurrentThemePackFilename, pack_path); |
} |
void BrowserThemeProvider::SaveThemeID(const std::string& id) { |
profile_->GetPrefs()->SetString(prefs::kCurrentThemeID, UTF8ToWide(id)); |
} |
-void BrowserThemeProvider::ClearCaches() { |
- FreePlatformCaches(); |
- STLDeleteValues(&image_cache_); |
- |
- // Scope for AutoLock on themed_image_cache. |
- { |
- AutoLock lock(themed_image_cache_lock_); |
- STLDeleteValues(&themed_image_cache_); |
+void BrowserThemeProvider::BuildFromExtension(Extension* extension) { |
+ scoped_refptr<BrowserThemePack> pack = |
+ BrowserThemePack::BuildFromExtension(extension); |
+ if (!pack.get()) { |
+ NOTREACHED() << "Could not load theme."; |
+ return; |
} |
- images_disk_cache_.clear(); |
-} |
- |
-void BrowserThemeProvider::WriteImagesToDisk() const { |
- g_browser_process->file_thread()->message_loop()->PostTask(FROM_HERE, |
- new WriteImagesToDiskTask(images_disk_cache_, themed_image_cache_)); |
- SaveCachedImageData(); |
-} |
+ // Write the packed file to disk. |
+ FilePath pack_path = extension->path().Append(chrome::kThemePackFilename); |
+ ChromeThread::PostTask(ChromeThread::IO, FROM_HERE, |
+ new WritePackToDiskTask(pack, pack_path)); |
-bool BrowserThemeProvider::ShouldTintFrames() const { |
- return (HasCustomImage(IDR_THEME_FRAME) || |
- tints_.count(GetTintKey(TINT_BACKGROUND_TAB)) || |
- tints_.count(GetTintKey(TINT_FRAME)) || |
- tints_.count(GetTintKey(TINT_FRAME_INACTIVE)) || |
- tints_.count(GetTintKey(TINT_FRAME_INCOGNITO)) || |
- tints_.count(GetTintKey(TINT_FRAME_INCOGNITO_INACTIVE))); |
+ SavePackName(pack_path); |
+ theme_pack_ = pack; |
} |