Chromium Code Reviews| Index: ash/system/chromeos/network/network_icon.cc |
| diff --git a/ash/system/chromeos/network/network_icon.cc b/ash/system/chromeos/network/network_icon.cc |
| index 73abc8456412a6f6b083abb1b2bd33ca6dcce0de..96f5fd01c443b49feaedb51ed24941a7319567d1 100644 |
| --- a/ash/system/chromeos/network/network_icon.cc |
| +++ b/ash/system/chromeos/network/network_icon.cc |
| @@ -18,6 +18,7 @@ |
| #include "third_party/cros_system_api/dbus/service_constants.h" |
| #include "ui/base/l10n/l10n_util.h" |
| #include "ui/base/resource/resource_bundle.h" |
| +#include "ui/base/webui/web_ui_util.h" |
| #include "ui/gfx/canvas.h" |
| #include "ui/gfx/image/image_skia_operations.h" |
| #include "ui/gfx/image/image_skia_source.h" |
| @@ -55,12 +56,15 @@ struct Badges { |
| // class used for maintaining a map of network state and images. |
| class NetworkIconImpl { |
| public: |
| - explicit NetworkIconImpl(IconType icon_type); |
| + NetworkIconImpl(const std::string& path, IconType icon_type); |
| // Determines whether or not the associated network might be dirty and if so |
| // updates and generates the icon. Does nothing if network no longer exists. |
| void Update(const chromeos::NetworkState* network); |
| + // Returns the cached image url for |image_| based on |scale_factor|. |
| + const std::string& GetImageUrl(float scale_factor); |
| + |
| const gfx::ImageSkia& image() const { return image_; } |
| private: |
| @@ -82,6 +86,9 @@ class NetworkIconImpl { |
| // Gets the appropriate icon and badges and composites the image. |
| void GenerateImage(const chromeos::NetworkState* network); |
| + // Network path, used for debugging. |
| + std::string network_path_; |
| + |
| // Defines color theme and VPN badging |
| const IconType icon_type_; |
| @@ -106,6 +113,11 @@ class NetworkIconImpl { |
| // Generated icon image. |
| gfx::ImageSkia image_; |
| + // Map of cached image urls by scale factor. Cleared whenever image_ is |
| + // generated. |
| + typedef std::map<float, std::string> ImageUrlMap; |
|
Nikita (slow)
2014/06/06 16:17:26
nit: Move typedef to the top of private section.
stevenjb
2014/06/06 16:44:56
Done.
|
| + ImageUrlMap image_urls_; |
| + |
| DISALLOW_COPY_AND_ASSIGN(NetworkIconImpl); |
| }; |
| @@ -257,6 +269,28 @@ class NetworkIconImageSource : public gfx::ImageSkiaSource { |
| //------------------------------------------------------------------------------ |
| // Utilities for extracting icon images. |
| +// A struct used for caching image urls. |
| +struct ImageIdForNetworkType { |
| + ImageIdForNetworkType(IconType icon_type, |
| + const std::string& network_type, |
| + float scale_factor) : |
| + icon_type(icon_type), |
| + network_type(network_type), |
| + scale_factor(scale_factor) {} |
| + bool operator<(const ImageIdForNetworkType& other) const { |
| + if (icon_type != other.icon_type) |
| + return icon_type < other.icon_type; |
| + if (network_type != other.network_type) |
| + return network_type < other.network_type; |
| + return scale_factor < other.scale_factor; |
| + } |
| + IconType icon_type; |
| + std::string network_type; |
| + float scale_factor; |
| +}; |
| + |
| +typedef std::map<ImageIdForNetworkType, std::string> ImageIdUrlMap; |
| + |
| bool IconTypeIsDark(IconType icon_type) { |
| return (icon_type != ICON_TYPE_TRAY); |
| } |
| @@ -306,29 +340,49 @@ gfx::ImageSkia GetImageForIndex(ImageType image_type, |
| gfx::Rect(0, index * height, width, height)); |
| } |
| -const gfx::ImageSkia GetConnectedImage(const std::string& type, |
| - IconType icon_type) { |
| - if (type == shill::kTypeVPN) { |
| +const gfx::ImageSkia GetConnectedImage(IconType icon_type, |
| + const std::string& network_type) { |
| + if (network_type == shill::kTypeVPN) { |
| return *ui::ResourceBundle::GetSharedInstance().GetImageSkiaNamed( |
| IDR_AURA_UBER_TRAY_NETWORK_VPN); |
| } |
| - ImageType image_type = ImageTypeForNetworkType(type); |
| + ImageType image_type = ImageTypeForNetworkType(network_type); |
| const int connected_index = NumImagesForType(image_type) - 1; |
| return GetImageForIndex(image_type, icon_type, connected_index); |
| } |
| -const gfx::ImageSkia GetDisconnectedImage(const std::string& type, |
| - IconType icon_type) { |
| - if (type == shill::kTypeVPN) { |
| +const gfx::ImageSkia GetDisconnectedImage(IconType icon_type, |
| + const std::string& network_type) { |
| + if (network_type == shill::kTypeVPN) { |
| // Note: same as connected image, shouldn't normally be seen. |
| return *ui::ResourceBundle::GetSharedInstance().GetImageSkiaNamed( |
| IDR_AURA_UBER_TRAY_NETWORK_VPN); |
| } |
| - ImageType image_type = ImageTypeForNetworkType(type); |
| + ImageType image_type = ImageTypeForNetworkType(network_type); |
| const int disconnected_index = 0; |
| return GetImageForIndex(image_type, icon_type, disconnected_index); |
| } |
| +const std::string& GetDisconnectedImageUrl(IconType icon_type, |
| + const std::string& network_type, |
| + float scale_factor) { |
| + static ImageIdUrlMap* s_image_url_map = NULL; |
| + if (s_image_url_map == NULL) |
| + s_image_url_map = new ImageIdUrlMap; |
| + |
| + ImageIdForNetworkType key(icon_type, network_type, scale_factor); |
| + ImageIdUrlMap::iterator iter = s_image_url_map->find(key); |
| + if (iter != s_image_url_map->end()) |
| + return iter->second; |
| + |
| + VLOG(2) << "Generating disconnected bitmap URL for: " << network_type; |
| + gfx::ImageSkia image = GetDisconnectedImage(icon_type, network_type); |
| + gfx::ImageSkiaRep image_rep = image.GetRepresentation(scale_factor); |
| + iter = s_image_url_map->insert(std::make_pair( |
| + key, webui::GetBitmapDataUrl(image_rep.sk_bitmap()))).first; |
| + return iter->second; |
| +} |
| + |
| gfx::ImageSkia* ConnectingWirelessImage(ImageType image_type, |
| IconType icon_type, |
| double animation) { |
| @@ -509,8 +563,8 @@ gfx::ImageSkia GetConnectingVpnImage(IconType icon_type) { |
| } |
| } |
| -gfx::ImageSkia GetConnectingImage(const std::string& network_type, |
| - IconType icon_type) { |
| +gfx::ImageSkia GetConnectingImage(IconType icon_type, |
| + const std::string& network_type) { |
| if (network_type == shill::kTypeVPN) |
| return GetConnectingVpnImage(icon_type); |
| @@ -523,19 +577,30 @@ gfx::ImageSkia GetConnectingImage(const std::string& network_type, |
| new NetworkIconImageSource(*icon, Badges()), icon->size()); |
| } |
| +std::string GetConnectingImageUrl(IconType icon_type, |
| + const std::string& network_type, |
| + float scale_factor) { |
| + // Caching the connecting image is complicated and we will never draw more |
| + // than a few per frame, so just generate the image url each time. |
| + gfx::ImageSkia image = GetConnectingImage(icon_type, network_type); |
| + gfx::ImageSkiaRep image_rep = image.GetRepresentation(scale_factor); |
| + return webui::GetBitmapDataUrl(image_rep.sk_bitmap()); |
| +} |
| + |
| } // namespace |
| //------------------------------------------------------------------------------ |
| // NetworkIconImpl |
| -NetworkIconImpl::NetworkIconImpl(IconType icon_type) |
| - : icon_type_(icon_type), |
| +NetworkIconImpl::NetworkIconImpl(const std::string& path, IconType icon_type) |
| + : network_path_(path), |
| + icon_type_(icon_type), |
| strength_index_(-1), |
| technology_badge_(NULL), |
| vpn_badge_(NULL), |
| behind_captive_portal_(false) { |
| // Default image |
| - image_ = GetDisconnectedImage(shill::kTypeWifi, icon_type); |
| + image_ = GetDisconnectedImage(icon_type, shill::kTypeWifi); |
| } |
| void NetworkIconImpl::Update(const NetworkState* network) { |
| @@ -674,24 +739,30 @@ void NetworkIconImpl::GenerateImage(const NetworkState* network) { |
| GetBadges(network, &badges); |
| image_ = gfx::ImageSkia( |
| new NetworkIconImageSource(icon, badges), icon.size()); |
| + image_urls_.clear(); |
| } |
| -//------------------------------------------------------------------------------ |
| -// Public interface |
| +const std::string& NetworkIconImpl::GetImageUrl(float scale_factor) { |
| + ImageUrlMap::iterator iter = image_urls_.find(scale_factor); |
| + if (iter != image_urls_.end()) |
| + return iter->second; |
| + VLOG(2) << "Generating bitmap URL for: " << network_path_; |
|
Nikita (slow)
2014/06/06 16:17:26
nit: insert empty line before VLOG
stevenjb
2014/06/06 16:44:56
Done.
|
| + gfx::ImageSkiaRep image_rep = image_.GetRepresentation(scale_factor); |
| + iter = image_urls_.insert(std::make_pair( |
| + scale_factor, webui::GetBitmapDataUrl(image_rep.sk_bitmap()))).first; |
| + return iter->second; |
| +} |
| -gfx::ImageSkia GetImageForNetwork(const NetworkState* network, |
| - IconType icon_type) { |
| - DCHECK(network); |
| - // Handle connecting icons. |
| - if (network->IsConnectingState()) |
| - return GetConnectingImage(network->type(), icon_type); |
| +namespace { |
| +NetworkIconImpl* FindAndUpdateImageImpl(const NetworkState* network, |
| + IconType icon_type) { |
| // Find or add the icon. |
| NetworkIconMap* icon_map = GetIconMap(icon_type); |
| NetworkIconImpl* icon; |
| NetworkIconMap::iterator iter = icon_map->find(network->path()); |
| if (iter == icon_map->end()) { |
| - icon = new NetworkIconImpl(icon_type); |
| + icon = new NetworkIconImpl(network->path(), icon_type); |
| icon_map->insert(std::make_pair(network->path(), icon)); |
| } else { |
| icon = iter->second; |
| @@ -699,22 +770,56 @@ gfx::ImageSkia GetImageForNetwork(const NetworkState* network, |
| // Update and return the icon's image. |
| icon->Update(network); |
| + return icon; |
| +} |
| + |
| +} // namespace |
| + |
| +//------------------------------------------------------------------------------ |
| +// Public interface |
| + |
| +gfx::ImageSkia GetImageForNetwork(const NetworkState* network, |
| + IconType icon_type) { |
| + DCHECK(network); |
| + // Handle connecting icons. |
| + if (network->IsConnectingState()) |
| + return GetConnectingImage(icon_type, network->type()); |
| + |
| + NetworkIconImpl* icon = FindAndUpdateImageImpl(network, icon_type); |
| return icon->image(); |
| } |
| +std::string GetImageUrlForNetwork(const NetworkState* network, |
| + IconType icon_type, |
| + float scale_factor) { |
| + DCHECK(network); |
| + // Handle connecting icons. |
| + if (network->IsConnectingState()) |
| + return GetConnectingImageUrl(icon_type, network->type(), scale_factor); |
| + |
| + NetworkIconImpl* icon = FindAndUpdateImageImpl(network, icon_type); |
| + return icon->GetImageUrl(scale_factor); |
| +} |
| + |
| gfx::ImageSkia GetImageForConnectedNetwork(IconType icon_type, |
| const std::string& network_type) { |
| - return GetConnectedImage(network_type, icon_type); |
| + return GetConnectedImage(icon_type, network_type); |
| } |
| gfx::ImageSkia GetImageForConnectingNetwork(IconType icon_type, |
| const std::string& network_type) { |
| - return GetConnectingImage(network_type, icon_type); |
| + return GetConnectingImage(icon_type, network_type); |
| } |
| gfx::ImageSkia GetImageForDisconnectedNetwork(IconType icon_type, |
| const std::string& network_type) { |
| - return GetDisconnectedImage(network_type, icon_type); |
| + return GetDisconnectedImage(icon_type, network_type); |
| +} |
| + |
| +std::string GetImageUrlForDisconnectedNetwork(IconType icon_type, |
| + const std::string& network_type, |
| + float scale_factor) { |
| + return GetDisconnectedImageUrl(icon_type, network_type, scale_factor); |
| } |
| base::string16 GetLabelForNetwork(const chromeos::NetworkState* network, |