diff options
author | stevenjb@google.com <stevenjb@google.com@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-07-19 19:50:24 +0000 |
---|---|---|
committer | stevenjb@google.com <stevenjb@google.com@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-07-19 19:50:24 +0000 |
commit | 2e9c23f5c7049beead982ee0834b7e91395debee (patch) | |
tree | dd590cb3ff95387943d759404279e3572aa8f30d | |
parent | 4c4d4085ca49d09a1fc6aee59161f3baa9e348fa (diff) | |
download | chromium_src-2e9c23f5c7049beead982ee0834b7e91395debee.zip chromium_src-2e9c23f5c7049beead982ee0834b7e91395debee.tar.gz chromium_src-2e9c23f5c7049beead982ee0834b7e91395debee.tar.bz2 |
Move network icon code to NetworkIcon class.
BUG=chromium-os:17262
TEST=Thoroughly test network icons in OOBE screen, network menu (pre and post login), and settings/internet.
This class should have unit tests, however due to dependencies on NetworkLibrary (see http://code.google.com/p/chromium-os/issues/detail?id=17354), they will be added separately (http://code.google.com/p/chromium-os/issues/detail?id=17355)
Review URL: http://codereview.chromium.org/7314025
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@93079 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r-- | chrome/browser/chromeos/cros/cros_mock.cc | 6 | ||||
-rw-r--r-- | chrome/browser/chromeos/cros/mock_network_library.h | 1 | ||||
-rw-r--r-- | chrome/browser/chromeos/cros/network_library.cc | 17 | ||||
-rw-r--r-- | chrome/browser/chromeos/cros/network_library.h | 25 | ||||
-rw-r--r-- | chrome/browser/chromeos/status/network_dropdown_button.cc | 104 | ||||
-rw-r--r-- | chrome/browser/chromeos/status/network_dropdown_button.h | 35 | ||||
-rw-r--r-- | chrome/browser/chromeos/status/network_menu.cc | 456 | ||||
-rw-r--r-- | chrome/browser/chromeos/status/network_menu.h | 59 | ||||
-rw-r--r-- | chrome/browser/chromeos/status/network_menu_button.cc | 189 | ||||
-rw-r--r-- | chrome/browser/chromeos/status/network_menu_button.h | 68 | ||||
-rw-r--r-- | chrome/browser/chromeos/status/network_menu_icon.cc | 682 | ||||
-rw-r--r-- | chrome/browser/chromeos/status/network_menu_icon.h | 77 | ||||
-rw-r--r-- | chrome/browser/ui/webui/chromeos/mobile_setup_ui.cc | 8 | ||||
-rw-r--r-- | chrome/browser/ui/webui/options/chromeos/internet_options_handler.cc | 23 | ||||
-rw-r--r-- | chrome/chrome_browser.gypi | 2 |
15 files changed, 953 insertions, 799 deletions
diff --git a/chrome/browser/chromeos/cros/cros_mock.cc b/chrome/browser/chromeos/cros/cros_mock.cc index bfb03a9..fc16038 100644 --- a/chrome/browser/chromeos/cros/cros_mock.cc +++ b/chrome/browser/chromeos/cros/cros_mock.cc @@ -173,6 +173,9 @@ void CrosMock::SetNetworkLibraryStatusAreaExpectations() { EXPECT_CALL(*mock_network_library_, active_network()) .Times(AnyNumber()) .WillRepeatedly((Return((const Network*)(NULL)))); + EXPECT_CALL(*mock_network_library_, ethernet_network()) + .Times(AnyNumber()) + .WillRepeatedly((Return((const EthernetNetwork*)(NULL)))); EXPECT_CALL(*mock_network_library_, wifi_network()) .Times(AnyNumber()) .WillRepeatedly((Return((const WifiNetwork*)(NULL)))); @@ -194,6 +197,9 @@ void CrosMock::SetNetworkLibraryStatusAreaExpectations() { EXPECT_CALL(*mock_network_library_, connected_network()) .Times(AnyNumber()) .WillRepeatedly((Return((const Network*)(NULL)))); + EXPECT_CALL(*mock_network_library_, connecting_network()) + .Times(AnyNumber()) + .WillRepeatedly((Return((const Network*)(NULL)))); // Set specific expectations for interesting functions: diff --git a/chrome/browser/chromeos/cros/mock_network_library.h b/chrome/browser/chromeos/cros/mock_network_library.h index 2410da2..7b58f20 100644 --- a/chrome/browser/chromeos/cros/mock_network_library.h +++ b/chrome/browser/chromeos/cros/mock_network_library.h @@ -146,6 +146,7 @@ class MockNetworkLibrary : public NetworkLibrary { MOCK_CONST_METHOD0(active_network, const Network*(void)); MOCK_CONST_METHOD0(connected_network, const Network*(void)); + MOCK_CONST_METHOD0(connecting_network, const Network*(void)); MOCK_CONST_METHOD0(offline_mode, bool(void)); diff --git a/chrome/browser/chromeos/cros/network_library.cc b/chrome/browser/chromeos/cros/network_library.cc index 4ad7877..78cd61f 100644 --- a/chrome/browser/chromeos/cros/network_library.cc +++ b/chrome/browser/chromeos/cros/network_library.cc @@ -2673,10 +2673,10 @@ class NetworkLibraryImplBase : public NetworkLibrary { return remembered_virtual_networks_; } + // Use flimflam's ordering of the services to determine which type of + // network to return (i.e. don't assume priority of network types). // Note: This does not include any virtual networks. virtual const Network* active_network() const OVERRIDE { - // Use flimflam's ordering of the services to determine what the active - // network is (i.e. don't assume priority of network types). Network* result = NULL; if (ethernet_ && ethernet_->is_active()) result = ethernet_; @@ -2692,8 +2692,6 @@ class NetworkLibraryImplBase : public NetworkLibrary { } virtual const Network* connected_network() const OVERRIDE { - // Use flimflam's ordering of the services to determine what the connected - // network is (i.e. don't assume priority of network types). Network* result = NULL; if (ethernet_ && ethernet_->connected()) result = ethernet_; @@ -2708,6 +2706,17 @@ class NetworkLibraryImplBase : public NetworkLibrary { return result; } + // Connecting order in logical prefernce. + virtual const Network* connecting_network() const { + if (ethernet_connecting()) + return ethernet_network(); + else if (wifi_connecting()) + return wifi_network(); + else if (cellular_connecting()) + return cellular_network(); + return NULL; + } + virtual bool ethernet_available() const OVERRIDE { return available_devices_ & (1 << TYPE_ETHERNET); } diff --git a/chrome/browser/chromeos/cros/network_library.h b/chrome/browser/chromeos/cros/network_library.h index 2a28ca0..cb0a315 100644 --- a/chrome/browser/chromeos/cros/network_library.h +++ b/chrome/browser/chromeos/cros/network_library.h @@ -327,14 +327,10 @@ class Network { ConnectionState connection_state() const { return state_; } bool connecting() const { return IsConnectingState(state_); } bool configuring() const { return state_ == STATE_CONFIGURATION; } - bool connected() const { return state_ == STATE_READY || - state_ == STATE_ONLINE || - state_ == STATE_PORTAL; } + bool connected() const { return IsConnectedState(state_); } bool connecting_or_connected() const { return connecting() || connected(); } bool failed() const { return state_ == STATE_FAILURE; } - bool failed_or_disconnected() const { - return failed() || state_ == STATE_IDLE; - } + bool disconnected() const { return IsDisconnectedState(state_); } bool ready() const { return state_ == STATE_READY; } bool online() const { return state_ == STATE_ONLINE; } bool restricted_pool() const { return state_ == STATE_PORTAL; } @@ -382,12 +378,24 @@ class Network { // Copy any credentials from a remembered network that are unset in |this|. virtual void CopyCredentialsFromRemembered(Network* remembered); - // Static helper function. + // Static helper functions. + static bool IsConnectedState(ConnectionState state) { + return (state == STATE_READY || + state == STATE_ONLINE || + state == STATE_PORTAL); + } static bool IsConnectingState(ConnectionState state) { return (state == STATE_ASSOCIATION || state == STATE_CONFIGURATION || state == STATE_CARRIER); } + static bool IsDisconnectedState(ConnectionState state) { + return (state == STATE_UNKNOWN || + state == STATE_IDLE || + state == STATE_DISCONNECT || + state == STATE_FAILURE || + state == STATE_ACTIVATION_FAILURE); + } // Sends the well-known TPM PIN to flimflam via D-Bus, because flimflam may // need it to access client certificates in the TPM for 802.1X, VPN, etc. @@ -594,7 +602,7 @@ class WirelessNetwork : public Network { WirelessNetwork(const std::string& service_path, ConnectionType type) : Network(service_path, type), strength_(0) {} - int strength_; + int strength_; // 0-100 // Network overrides. virtual bool ParseValue(int index, const base::Value* value); @@ -1061,6 +1069,7 @@ class NetworkLibrary { virtual const Network* active_network() const = 0; virtual const Network* connected_network() const = 0; + virtual const Network* connecting_network() const = 0; virtual bool ethernet_available() const = 0; virtual bool wifi_available() const = 0; diff --git a/chrome/browser/chromeos/status/network_dropdown_button.cc b/chrome/browser/chromeos/status/network_dropdown_button.cc index f75edd2..6f53876 100644 --- a/chrome/browser/chromeos/status/network_dropdown_button.cc +++ b/chrome/browser/chromeos/status/network_dropdown_button.cc @@ -12,16 +12,7 @@ #include "chrome/browser/chromeos/status/status_area_host.h" #include "chrome/common/chrome_switches.h" #include "grit/generated_resources.h" -#include "grit/theme_resources.h" #include "ui/base/l10n/l10n_util.h" -#include "ui/base/resource/resource_bundle.h" -#include "ui/gfx/canvas_skia.h" - -namespace { - -const int kThrobDuration = 750; - -} // namespace namespace chromeos { @@ -36,13 +27,11 @@ NetworkDropdownButton::NetworkDropdownButton(bool is_browser_mode, IDS_STATUSBAR_NO_NETWORKS_MESSAGE)), this, true), - ALLOW_THIS_IN_INITIALIZER_LIST(animation_connecting_(this)), parent_window_(parent_window), - should_show_options_(should_show_options), - last_network_type_(TYPE_WIFI) { + should_show_options_(should_show_options) { network_menu_.reset(new NetworkMenu(this, is_browser_mode)); - animation_connecting_.SetThrobDuration(kThrobDuration); - animation_connecting_.SetTweenType(ui::Tween::LINEAR); + network_icon_.reset( + new NetworkMenuIcon(this, NetworkMenuIcon::DROPDOWN_MODE)); CrosLibrary::Get()->GetNetworkLibrary()->AddNetworkManagerObserver(this); // The initial state will be updated on Refresh. // See network_selection_view.cc. @@ -52,20 +41,6 @@ NetworkDropdownButton::~NetworkDropdownButton() { CrosLibrary::Get()->GetNetworkLibrary()->RemoveNetworkManagerObserver(this); } -//////////////////////////////////////////////////////////////////////////////// -// NetworkDropdownButton, ui::AnimationDelegate implementation: - -void NetworkDropdownButton::AnimationProgressed( - const ui::Animation* animation) { - if (animation == &animation_connecting_) { - SetIcon(*NetworkMenu::IconForNetworkConnecting( - animation_connecting_.GetCurrentValue(), last_network_type_)); - SchedulePaint(); - } else { - MenuButton::AnimationProgressed(animation); - } -} - void NetworkDropdownButton::Refresh() { OnNetworkManagerChanged(CrosLibrary::Get()->GetNetworkLibrary()); } @@ -126,64 +101,29 @@ void NetworkDropdownButton::OnDialogClosed() { // NetworkDropdownButton, NetworkLibrary::NetworkManagerObserver implementation: void NetworkDropdownButton::OnNetworkManagerChanged(NetworkLibrary* cros) { - // Show network that we will actually use. It could be another network than - // user selected. For example user selected WiFi network but we have Ethernet - // connection and Chrome OS device will actually use Ethernet. - // This gets called on initialization, so any changes should be reflected // in CrosMock::SetNetworkLibraryStatusAreaExpectations(). - - ResourceBundle& rb = ResourceBundle::GetSharedInstance(); - if (CrosLibrary::Get()->EnsureLoaded()) { - // Always show the active network, if any - const Network* active_network = cros->active_network(); - last_network_type_ = NetworkMenu::TypeForNetwork(active_network); - if (active_network != NULL) { - animation_connecting_.Stop(); - if (active_network->type() == TYPE_ETHERNET) { - SetIcon(*rb.GetBitmapNamed(IDR_STATUSBAR_WIRED)); - SetText(UTF16ToWide( - l10n_util::GetStringUTF16(IDS_STATUSBAR_NETWORK_DEVICE_ETHERNET))); - } else if (active_network->type() == TYPE_WIFI) { - const WifiNetwork* wifi = - static_cast<const WifiNetwork*>(active_network); - SetIcon(*NetworkMenu::IconForNetworkStrength(wifi)); - SetText(UTF8ToWide(wifi->name())); - } else if (active_network->type() == TYPE_CELLULAR) { - const CellularNetwork* cellular = - static_cast<const CellularNetwork*>(active_network); - SetIcon(*NetworkMenu::IconForNetworkStrength(cellular)); - SetText(UTF8ToWide(cellular->name())); - } else { - NOTREACHED(); - } - } else if (cros->wifi_connecting() || cros->cellular_connecting()) { - if (!animation_connecting_.is_animating()) { - animation_connecting_.Reset(); - animation_connecting_.StartThrobbing(-1); - SetIcon(*NetworkMenu::IconForNetworkConnecting(0, last_network_type_)); - } - if (cros->wifi_connecting()) - SetText(UTF8ToWide(cros->wifi_network()->name())); - else if (cros->cellular_connecting()) - SetText(UTF8ToWide(cros->cellular_network()->name())); - } - - if (!cros->Connected() && !cros->Connecting()) { - animation_connecting_.Stop(); - SetIcon(SkBitmap()); - SetText(UTF16ToWide( - l10n_util::GetStringUTF16(IDS_NETWORK_SELECTION_NONE))); - } - } else { - animation_connecting_.Stop(); - SetIcon(SkBitmap()); - SetText(UTF16ToWide( - l10n_util::GetStringUTF16(IDS_STATUSBAR_NO_NETWORKS_MESSAGE))); - } - + SetNetworkIconAndText(); SchedulePaint(); network_menu_->UpdateMenu(); } +//////////////////////////////////////////////////////////////////////////////// +// NetworkDropdownButton, NetworkMenuIcon::Delegate implementation: +void NetworkDropdownButton::NetworkMenuIconChanged() { + const SkBitmap* bitmap = network_icon_->GetIconAndText(NULL); + SetIcon(*bitmap); + SchedulePaint(); +} + +//////////////////////////////////////////////////////////////////////////////// +// NetworkDropdownButton, private methods: + +void NetworkDropdownButton::SetNetworkIconAndText() { + string16 text; + const SkBitmap* bitmap = network_icon_->GetIconAndText(&text); + SetIcon(*bitmap); + SetText(UTF16ToWide(text)); +} + } // namespace chromeos diff --git a/chrome/browser/chromeos/status/network_dropdown_button.h b/chrome/browser/chromeos/status/network_dropdown_button.h index 2c955d9..c96317e 100644 --- a/chrome/browser/chromeos/status/network_dropdown_button.h +++ b/chrome/browser/chromeos/status/network_dropdown_button.h @@ -10,9 +10,8 @@ #include "chrome/browser/chromeos/cros/network_library.h" #include "chrome/browser/chromeos/login/login_html_dialog.h" #include "chrome/browser/chromeos/status/network_menu.h" +#include "chrome/browser/chromeos/status/network_menu_icon.h" #include "chrome/browser/chromeos/views/dropdown_button.h" -#include "ui/base/animation/animation_delegate.h" -#include "ui/base/animation/throb_animation.h" namespace chromeos { @@ -23,6 +22,7 @@ namespace chromeos { class NetworkDropdownButton : public DropDownButton, public views::ViewMenuDelegate, public NetworkMenu::Delegate, + public NetworkMenuIcon::Delegate, public NetworkLibrary::NetworkManagerObserver, public LoginHtmlDialog::Delegate { public: @@ -31,12 +31,6 @@ class NetworkDropdownButton : public DropDownButton, bool should_show_options); virtual ~NetworkDropdownButton(); - // ui::AnimationDelegate implementation. - virtual void AnimationProgressed(const ui::Animation* animation); - - // NetworkLibrary::NetworkManagerObserver implementation. - virtual void OnNetworkManagerChanged(NetworkLibrary* obj); - void SetFirstLevelMenuWidth(int width); void CancelMenu(); @@ -44,14 +38,20 @@ class NetworkDropdownButton : public DropDownButton, // Refreshes button state. Used when language has been changed. void Refresh(); + // NetworkLibrary::NetworkManagerObserver implementation. + virtual void OnNetworkManagerChanged(NetworkLibrary* obj) OVERRIDE; + // NetworkMenu::Delegate implementation: - virtual views::MenuButton* GetMenuButton(); - virtual gfx::NativeWindow GetNativeWindow() const; - virtual void OpenButtonOptions(); - virtual bool ShouldOpenButtonOptions() const; + virtual views::MenuButton* GetMenuButton() OVERRIDE; + virtual gfx::NativeWindow GetNativeWindow() const OVERRIDE; + virtual void OpenButtonOptions() OVERRIDE; + virtual bool ShouldOpenButtonOptions() const OVERRIDE; + + // NetworkMenuIcon::Delegate implementation: + virtual void NetworkMenuIconChanged() OVERRIDE; // views::ViewMenuDelegate implementation. - virtual void RunMenu(views::View* source, const gfx::Point& pt); + virtual void RunMenu(views::View* source, const gfx::Point& pt) OVERRIDE; protected: // Overridden from views::View. @@ -61,20 +61,19 @@ class NetworkDropdownButton : public DropDownButton, virtual void OnDialogClosed() OVERRIDE; private: + void SetNetworkIconAndText(); + // The Network menu. scoped_ptr<NetworkMenu> network_menu_; - // The throb animation that does the wifi connecting animation. - ui::ThrobAnimation animation_connecting_; + // The Network menu icon. + scoped_ptr<NetworkMenuIcon> network_icon_; gfx::NativeWindow parent_window_; // If true things like proxy settings menu item will be supported. bool should_show_options_; - // The last network we connected to (or tried to). - ConnectionType last_network_type_; - // Proxy settings dialog that can be invoked from network menu. scoped_ptr<LoginHtmlDialog> proxy_settings_dialog_; diff --git a/chrome/browser/chromeos/status/network_menu.cc b/chrome/browser/chromeos/status/network_menu.cc index dbd6f27..0181263 100644 --- a/chrome/browser/chromeos/status/network_menu.cc +++ b/chrome/browser/chromeos/status/network_menu.cc @@ -15,6 +15,7 @@ #include "chrome/browser/chromeos/customization_document.h" #include "chrome/browser/chromeos/options/network_config_view.h" #include "chrome/browser/chromeos/sim_dialog_delegate.h" +#include "chrome/browser/chromeos/status/network_menu_icon.h" #include "chrome/browser/defaults.h" #include "chrome/browser/ui/browser.h" #include "chrome/browser/ui/browser_list.h" @@ -37,58 +38,6 @@ namespace { -// Amount to fade icons while connecting. -const double kConnectingImageAlpha = 0.5; - -// Network strength bars images. -const int kNumBarsImages = 4; - -// NOTE: Use an array rather than just calculating a resource number to avoid -// creating implicit ordering dependencies on the resource values. -const int kBarsImages[kNumBarsImages] = { - IDR_STATUSBAR_NETWORK_BARS1, - IDR_STATUSBAR_NETWORK_BARS2, - IDR_STATUSBAR_NETWORK_BARS3, - IDR_STATUSBAR_NETWORK_BARS4, -}; - -const int kBarsImagesOrange[kNumBarsImages] = { - IDR_STATUSBAR_NETWORK_BARS1_ORANGE, - IDR_STATUSBAR_NETWORK_BARS2_ORANGE, - IDR_STATUSBAR_NETWORK_BARS3_ORANGE, - IDR_STATUSBAR_NETWORK_BARS4_ORANGE, -}; - -SkBitmap kBarsImagesAnimating[kNumBarsImages]; - -// Network strength arcs images. -const int kNumArcsImages = 7; - -// NOTE: Use an array rather than just calculating a resource number to avoid -// creating implicit ordering dependencies on the resource values. -const int kArcsImages[kNumArcsImages] = { - IDR_STATUSBAR_NETWORK_ARCS1, - IDR_STATUSBAR_NETWORK_ARCS2, - IDR_STATUSBAR_NETWORK_ARCS3, - IDR_STATUSBAR_NETWORK_ARCS4, - IDR_STATUSBAR_NETWORK_ARCS5, - IDR_STATUSBAR_NETWORK_ARCS6, - IDR_STATUSBAR_NETWORK_ARCS7, -}; - -SkBitmap kArcsImagesAnimating[kNumArcsImages]; - -// Replace '&' in a string with "&&" to allow it to be a menu item label. -std::string EscapeAmpersands(const std::string& input) { - std::string str = input; - size_t found = str.find('&'); - while (found != std::string::npos) { - str.replace(found, 1, "&&"); - found = str.find('&', found + 2); - } - return str; -} - // Offsets for views menu ids (main menu and submenu ids use the same // namespace). const int kItemIndexMask = 0x0fff; @@ -104,6 +53,17 @@ const int kDefaultMinimumWidth = 280; const int kTopMargin = 5; const int kBottomMargin = 7; +// Replace '&' in a string with "&&" to allow it to be a menu item label. +std::string EscapeAmpersands(const std::string& input) { + std::string str = input; + size_t found = str.find('&'); + while (found != std::string::npos) { + str.replace(found, 1, "&&"); + found = str.find('&', found + 2); + } + return str; +} + } // namespace namespace chromeos { @@ -251,7 +211,7 @@ class NetworkMenuModel : public views::MenuDelegate { class MoreMenuModel : public NetworkMenuModel { public: - explicit MoreMenuModel(NetworkMenu* owner); + explicit MoreMenuModel(NetworkMenu* owner) : NetworkMenuModel(owner) {} virtual ~MoreMenuModel() {} // NetworkMenuModel implementation. @@ -277,15 +237,17 @@ class VPNMenuModel : public NetworkMenuModel { int index, int command_id) OVERRIDE; - static SkBitmap IconForDisplay(const Network* network); - private: DISALLOW_COPY_AND_ASSIGN(VPNMenuModel); }; class MainMenuModel : public NetworkMenuModel { public: - explicit MainMenuModel(NetworkMenu* owner); + explicit MainMenuModel(NetworkMenu* owner) + : NetworkMenuModel(owner), + vpn_menu_model_(new VPNMenuModel(owner)), + more_menu_model_(new MoreMenuModel(owner)) { + } virtual ~MainMenuModel() {} // NetworkMenuModel implementation. @@ -574,12 +536,6 @@ void NetworkMenuModel::ShowOther(ConnectionType type) const { //////////////////////////////////////////////////////////////////////////////// // MainMenuModel -MainMenuModel::MainMenuModel(NetworkMenu* owner) - : NetworkMenuModel(owner), - vpn_menu_model_(new VPNMenuModel(owner)), - more_menu_model_(new MoreMenuModel(owner)) { -} - const NetworkMenuModel* MainMenuModel::GetMenuItemModel(int id) const { if (id & kMoreIndexMask) return more_menu_model_.get(); @@ -625,16 +581,17 @@ void MainMenuModel::InitMenuItems(bool is_browser_mode, } else { label = l10n_util::GetStringUTF16(IDS_STATUSBAR_NETWORK_DEVICE_ETHERNET); } - const SkBitmap* icon = rb.GetBitmapNamed(IDR_STATUSBAR_WIRED_BLACK); - const SkBitmap* badge = ethernet_connecting || ethernet_connected ? - NULL : rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_DISCONNECTED); int flag = FLAG_ETHERNET; if (ethernet_connecting || ethernet_connected) flag |= FLAG_ASSOCIATED; - menu_items_.push_back( - MenuItem(ui::MenuModel::TYPE_COMMAND, label, - NetworkMenu::IconForDisplay(icon, badge), std::string(), - flag)); + const SkBitmap* icon; + if (cros->ethernet_network()) { + icon = NetworkMenuIcon::GetBitmap(cros->ethernet_network()); + } else { + icon = rb.GetBitmapNamed(IDR_STATUSBAR_WIRED); + } + menu_items_.push_back(MenuItem(ui::MenuModel::TYPE_COMMAND, + label, *icon, std::string(), flag)); } // Wifi Networks @@ -667,10 +624,6 @@ void MainMenuModel::InitMenuItems(bool is_browser_mode, } } - const SkBitmap* icon = - NetworkMenu::IconForNetworkStrength(wifi_networks[i]); - const SkBitmap* badge = wifi_networks[i]->encrypted() ? - rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_SECURE) : NULL; int flag = FLAG_WIFI; // If a network is not connectable (e.g. it requires certificates and // the user is not logged in), we disable it. @@ -679,10 +632,10 @@ void MainMenuModel::InitMenuItems(bool is_browser_mode, if (active_wifi && wifi_networks[i]->service_path() == active_wifi->service_path()) flag |= FLAG_ASSOCIATED; + const SkBitmap* icon = NetworkMenuIcon::GetBitmap(wifi_networks[i]); menu_items_.push_back( - MenuItem(ui::MenuModel::TYPE_COMMAND, label, - NetworkMenu::IconForDisplay(icon, badge), - wifi_networks[i]->service_path(), flag)); + MenuItem(ui::MenuModel::TYPE_COMMAND, + label, *icon, wifi_networks[i]->service_path(), flag)); } if (!separator_added && !menu_items_.empty()) menu_items_.push_back(MenuItem()); @@ -740,12 +693,6 @@ void MainMenuModel::InitMenuItems(bool is_browser_mode, } } - const SkBitmap* icon = - NetworkMenu::IconForNetworkStrength(cell_networks[i]); - const SkBitmap* badge = - NetworkMenu::BadgeForNetworkTechnology(cell_networks[i]); - const SkBitmap* roaming_badge = - NetworkMenu::BadgeForRoamingStatus(cell_networks[i]); int flag = FLAG_CELLULAR; bool isActive = active_cellular && cell_networks[i]->service_path() == active_cellular->service_path() && @@ -754,11 +701,10 @@ void MainMenuModel::InitMenuItems(bool is_browser_mode, active_cellular && active_cellular->SupportsDataPlan(); if (isActive) flag |= FLAG_ASSOCIATED; + const SkBitmap* icon = NetworkMenuIcon::GetBitmap(cell_networks[i]); menu_items_.push_back( - MenuItem(ui::MenuModel::TYPE_COMMAND, label, - NetworkMenu::IconForDisplay(icon, badge, roaming_badge, - NULL), - cell_networks[i]->service_path(), flag)); + MenuItem(ui::MenuModel::TYPE_COMMAND, + label, *icon, cell_networks[i]->service_path(), flag)); if (isActive && supports_data_plan) { label.clear(); if (active_cellular->needs_new_plan()) { @@ -833,11 +779,11 @@ void MainMenuModel::InitMenuItems(bool is_browser_mode, const Network* connected_network = cros->connected_network(); if (connected_network) { menu_items_.push_back(MenuItem()); // Separator + const SkBitmap* icon = NetworkMenuIcon::GetVpnBitmap(); menu_items_.push_back(MenuItem( ui::MenuModel::TYPE_SUBMENU, l10n_util::GetStringUTF16(IDS_STATUSBAR_NETWORK_PRIVATE_NETWORKS), - VPNMenuModel::IconForDisplay(connected_network), - vpn_menu_model_.get(), FLAG_NONE)); + *icon, vpn_menu_model_.get(), FLAG_NONE)); vpn_menu_model_->InitMenuItems( is_browser_mode, should_open_button_options); } @@ -882,8 +828,7 @@ void MainMenuModel::InitMenuItems(bool is_browser_mode, l10n_util::GetStringUTF16(IDS_STATUSBAR_NETWORK_DEVICE_CELLULAR)); SkBitmap icon; if (is_locked) { - icon = NetworkMenu::IconForDisplay( - rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_SECURE), NULL); + icon = *rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_SECURE); } menu_items_.push_back(MenuItem(ui::MenuModel::TYPE_COMMAND, label, icon, std::string(), FLAG_TOGGLE_CELLULAR)); @@ -979,7 +924,7 @@ void VPNMenuModel::InitMenuItems(bool is_browser_mode, // Populate our MenuItems with the current list of virtual networks. const VirtualNetworkVector& virtual_networks = cros->virtual_networks(); const VirtualNetwork* active_vpn = cros->virtual_network(); - SkBitmap icon = VPNMenuModel::IconForDisplay(connected_network); + bool separator_added = false; string16 label; @@ -1007,9 +952,10 @@ void VPNMenuModel::InitMenuItems(bool is_browser_mode, flag |= FLAG_DISABLED; if (active_vpn && vpn->service_path() == active_vpn->service_path()) flag |= FLAG_ASSOCIATED; + const SkBitmap* icon = NetworkMenuIcon::GetBitmap(vpn); menu_items_.push_back( - MenuItem(ui::MenuModel::TYPE_COMMAND, label, icon, vpn->service_path(), - flag)); + MenuItem(ui::MenuModel::TYPE_COMMAND, + label, *icon, vpn->service_path(), flag)); } // Add option to add/disconnect from vpn. @@ -1034,54 +980,9 @@ void VPNMenuModel::PopulateMenuItem( NetworkMenuModel::PopulateMenuItem(menu, index, vpn_command_id); } -// static -SkBitmap VPNMenuModel::IconForDisplay(const Network* network) { - ResourceBundle& rb = ResourceBundle::GetSharedInstance(); - const SkBitmap* icon = NULL; - const SkBitmap* bottom_right_badge = NULL; - const SkBitmap* top_left_badge = NULL; - // We know for sure |network| is the active network, so no more checking - // is needed by BadgeForPrivateNetworkStatus, hence pass in NULL. - const SkBitmap* bottom_left_badge = - NetworkMenu::BadgeForPrivateNetworkStatus(NULL); - - // We should always have an underlying network for VPN, but if we ever don't - // (presumably an edge case), just return an empty icon. - if (!network) - return SkBitmap(); - - switch (network->type()) { - case TYPE_ETHERNET : - icon = rb.GetBitmapNamed(IDR_STATUSBAR_WIRED_BLACK); - break; - case TYPE_WIFI : - icon = NetworkMenu::IconForNetworkStrength( - static_cast<const WifiNetwork*>(network)); - break; - case TYPE_CELLULAR : { - const CellularNetwork* cellular = - static_cast<const CellularNetwork*>(network); - icon = NetworkMenu::IconForNetworkStrength(cellular); - bottom_right_badge = NetworkMenu::BadgeForNetworkTechnology(cellular); - top_left_badge = NetworkMenu::BadgeForRoamingStatus(cellular); - break; - } - default: - LOG(WARNING) << "VPN not handled for connection type " << network->type(); - return SkBitmap(); - } - - return NetworkMenu::IconForDisplay(icon, bottom_right_badge, top_left_badge, - bottom_left_badge); -} - //////////////////////////////////////////////////////////////////////////////// // MoreMenuModel -MoreMenuModel::MoreMenuModel(NetworkMenu* owner) - : NetworkMenuModel(owner) { -} - void MoreMenuModel::InitMenuItems( bool is_browser_mode, bool should_open_button_options) { // This gets called on initialization, so any changes should be reflected @@ -1222,283 +1123,4 @@ void NetworkMenu::ShowTabbedNetworkSettings(const Network* network) const { browser->ShowOptionsTab(page); } -//////////////////////////////////////////////////////////////////////////////// -// NetworkMenu, static methods: - -// static -const SkBitmap* NetworkMenu::IconForNetworkStrength(const WifiNetwork* wifi) { - DCHECK(wifi); - if (wifi->strength() == 0) { - return ResourceBundle::GetSharedInstance().GetBitmapNamed( - IDR_STATUSBAR_NETWORK_ARCS0); - } - int index = static_cast<int>(wifi->strength() / 100.0 * - nextafter(static_cast<float>(kNumArcsImages), 0)); - index = std::max(std::min(index, kNumArcsImages - 1), 0); - return ResourceBundle::GetSharedInstance().GetBitmapNamed(kArcsImages[index]); -} - -// static -const SkBitmap* NetworkMenu::IconForNetworkStrength( - const CellularNetwork* cellular) { - DCHECK(cellular); - // If no data, then we show 0 bars. - if (cellular->strength() == 0 || - cellular->data_left() == CellularNetwork::DATA_NONE) { - return ResourceBundle::GetSharedInstance().GetBitmapNamed( - IDR_STATUSBAR_NETWORK_BARS0); - } - int index = static_cast<int>(cellular->strength() / 100.0 * - nextafter(static_cast<float>(kNumBarsImages), 0)); - index = std::max(std::min(index, kNumBarsImages - 1), 0); - return ResourceBundle::GetSharedInstance().GetBitmapNamed(kBarsImages[index]); -} - -// static -SkBitmap NetworkMenu::IconForNetwork(const Network* network) { - DCHECK(network); - - chromeos::NetworkLibrary* cros = - chromeos::CrosLibrary::Get()->GetNetworkLibrary(); - ResourceBundle& rb = ResourceBundle::GetSharedInstance(); - - const SkBitmap* icon; - const SkBitmap* bottom_right_badge = NULL; - const SkBitmap* bottom_left_badge = NULL; - - switch (network->type()) { - case TYPE_ETHERNET: { - icon = rb.GetBitmapNamed(IDR_STATUSBAR_WIRED_BLACK); - if (!network->connecting() && !network->connected()) - bottom_right_badge = - rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_DISCONNECTED); - bottom_left_badge = BadgeForPrivateNetworkStatus(network); - return IconForDisplay( - icon, bottom_right_badge, NULL, bottom_left_badge); - } - case TYPE_WIFI: { - const WifiNetwork* wifi = static_cast<const WifiNetwork*>(network); - icon = IconForNetworkStrength(wifi); - if (wifi->encrypted()) - bottom_right_badge = rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_SECURE); - bottom_left_badge = BadgeForPrivateNetworkStatus(wifi); - return IconForDisplay( - icon, bottom_right_badge, NULL, bottom_left_badge); - } - case TYPE_CELLULAR: { - const CellularNetwork* cellular = - static_cast<const CellularNetwork*>(network); - icon = IconForNetworkStrength(cellular); - bottom_right_badge = BadgeForNetworkTechnology(cellular); - const SkBitmap* roaming_badge = BadgeForRoamingStatus(cellular); - bottom_left_badge = BadgeForPrivateNetworkStatus(cellular); - return IconForDisplay( - icon, bottom_right_badge, roaming_badge, bottom_left_badge); - } - case TYPE_VPN: { - return VPNMenuModel::IconForDisplay(cros->connected_network()); - } - default: - LOG(WARNING) << "Request for icon for unsupported type: " - << network->type(); - icon = ResourceBundle::GetSharedInstance().GetBitmapNamed( - IDR_STATUSBAR_NETWORK_BARS0); - return *icon; - } -} - -// static -const SkBitmap* NetworkMenu::IconForNetworkConnecting(double animation_value, - ConnectionType type) { - // Fade bars a bit and show the different bar states. - int image_count; - const int* source_image_ids; - SkBitmap* images; - - if (type == TYPE_WIFI) { - image_count = kNumArcsImages; - source_image_ids = kArcsImages; - images = kArcsImagesAnimating; - } else { - image_count = kNumBarsImages; - source_image_ids = kBarsImages; - images = kBarsImagesAnimating; - } - int index = static_cast<int>(animation_value * - nextafter(static_cast<float>(image_count), 0)); - index = std::max(std::min(index, image_count - 1), 0); - - // Lazily cache images. - if (images[index].empty()) { - ResourceBundle& rb = ResourceBundle::GetSharedInstance(); - SkBitmap source = *rb.GetBitmapNamed(source_image_ids[index]); - - // Create an empty image to fade against. - SkBitmap empty_image; - empty_image.setConfig(SkBitmap::kARGB_8888_Config, - source.width(), - source.height(), - 0); - empty_image.allocPixels(); - empty_image.eraseARGB(0, 0, 0, 0); - - images[index] = - SkBitmapOperations::CreateBlendedBitmap( - empty_image, - source, - kConnectingImageAlpha); - } - return &images[index]; -} - -// static -const SkBitmap* NetworkMenu::BadgeForNetworkTechnology( - const CellularNetwork* cellular) { - if (!cellular) - return NULL; - - int id = -1; - switch (cellular->network_technology()) { - case NETWORK_TECHNOLOGY_EVDO: - switch (cellular->data_left()) { - case CellularNetwork::DATA_NONE: - id = IDR_STATUSBAR_NETWORK_3G_ERROR; - break; - case CellularNetwork::DATA_VERY_LOW: - case CellularNetwork::DATA_LOW: - case CellularNetwork::DATA_NORMAL: - id = IDR_STATUSBAR_NETWORK_3G; - break; - case CellularNetwork::DATA_UNKNOWN: - id = IDR_STATUSBAR_NETWORK_3G_UNKNOWN; - break; - } - break; - case NETWORK_TECHNOLOGY_1XRTT: - switch (cellular->data_left()) { - case CellularNetwork::DATA_NONE: - id = IDR_STATUSBAR_NETWORK_1X_ERROR; - break; - case CellularNetwork::DATA_VERY_LOW: - case CellularNetwork::DATA_LOW: - case CellularNetwork::DATA_NORMAL: - id = IDR_STATUSBAR_NETWORK_1X; - break; - case CellularNetwork::DATA_UNKNOWN: - id = IDR_STATUSBAR_NETWORK_1X_UNKNOWN; - break; - } - break; - // Note: we may not be able to obtain data usage info - // from GSM carriers, so there may not be a reason - // to create _ERROR or _UNKNOWN versions of the following - // icons. - case NETWORK_TECHNOLOGY_GPRS: - id = IDR_STATUSBAR_NETWORK_GPRS; - break; - case NETWORK_TECHNOLOGY_EDGE: - id = IDR_STATUSBAR_NETWORK_EDGE; - break; - case NETWORK_TECHNOLOGY_UMTS: - id = IDR_STATUSBAR_NETWORK_3G; - break; - case NETWORK_TECHNOLOGY_HSPA: - id = IDR_STATUSBAR_NETWORK_HSPA; - break; - case NETWORK_TECHNOLOGY_HSPA_PLUS: - id = IDR_STATUSBAR_NETWORK_HSPA_PLUS; - break; - case NETWORK_TECHNOLOGY_LTE: - id = IDR_STATUSBAR_NETWORK_LTE; - break; - case NETWORK_TECHNOLOGY_LTE_ADVANCED: - id = IDR_STATUSBAR_NETWORK_LTE_ADVANCED; - break; - case NETWORK_TECHNOLOGY_GSM: - id = IDR_STATUSBAR_NETWORK_GPRS; - break; - case NETWORK_TECHNOLOGY_UNKNOWN: - break; - } - if (id == -1) - return NULL; - else - return ResourceBundle::GetSharedInstance().GetBitmapNamed(id); -} - -// static -const SkBitmap* NetworkMenu::BadgeForRoamingStatus( - const CellularNetwork* cellular) { - if (cellular->roaming_state() == ROAMING_STATE_ROAMING) - return ResourceBundle::GetSharedInstance().GetBitmapNamed( - IDR_STATUSBAR_NETWORK_ROAMING); - else - return NULL; -} - -const SkBitmap* NetworkMenu::BadgeForPrivateNetworkStatus( - const Network* network) { - // If network is not null, check if it's the active network with vpn on it. - if (network) { - NetworkLibrary* cros = CrosLibrary::Get()->GetNetworkLibrary(); - if (!(cros->virtual_network() && network == cros->connected_network())) - return NULL; - } - // TODO(kuan): yellow lock icon not ready yet; for now, return the black one - // used by secure wifi network. - return ResourceBundle::GetSharedInstance().GetBitmapNamed( - IDR_STATUSBAR_NETWORK_SECURE); -} - -// static -SkBitmap NetworkMenu::IconForDisplay(const SkBitmap* icon, - const SkBitmap* badge) { - return IconForDisplay(icon, badge, NULL, NULL); -} - -// static -SkBitmap NetworkMenu::IconForDisplay(const SkBitmap* icon, - const SkBitmap* bottom_right_badge, - const SkBitmap* top_left_badge, - const SkBitmap* bottom_left_badge) { - DCHECK(icon); - if (bottom_right_badge == NULL && top_left_badge == NULL && - bottom_left_badge == NULL) - return *icon; - - static const int kTopLeftBadgeX = 0; - static const int kTopLeftBadgeY = 0; - static const int kBottomRightBadgeX = 14; - static const int kBottomRightBadgeY = 14; - static const int kBottomLeftBadgeX = 0; - static const int kBottomLeftBadgeY = 14; - - gfx::CanvasSkia canvas(icon->width(), icon->height(), false); - canvas.DrawBitmapInt(*icon, 0, 0); - if (bottom_right_badge != NULL) - canvas.DrawBitmapInt(*bottom_right_badge, - kBottomRightBadgeX, - kBottomRightBadgeY); - if (top_left_badge != NULL) - canvas.DrawBitmapInt(*top_left_badge, kTopLeftBadgeX, kTopLeftBadgeY); - if (bottom_left_badge != NULL) - canvas.DrawBitmapInt(*bottom_left_badge, kBottomLeftBadgeX, - kBottomLeftBadgeY); - return canvas.ExtractBitmap(); -} - -// static -ConnectionType NetworkMenu::TypeForNetwork(const Network* network) { - NetworkLibrary* cros = CrosLibrary::Get()->GetNetworkLibrary(); - if (network) - return network->type() == TYPE_CELLULAR ? TYPE_CELLULAR : TYPE_WIFI; - - // This way if both wifi and cell are connecting we'll use wifi. - if (cros->wifi_connecting()) - return TYPE_WIFI; - if (cros->cellular_connecting()) - return TYPE_CELLULAR; - return TYPE_WIFI; -} - } // namespace chromeos diff --git a/chrome/browser/chromeos/status/network_menu.h b/chrome/browser/chromeos/status/network_menu.h index 8ae2388..030d79a 100644 --- a/chrome/browser/chromeos/status/network_menu.h +++ b/chrome/browser/chromeos/status/network_menu.h @@ -100,64 +100,6 @@ class NetworkMenu { // Setters. void set_min_width(int min_width) { min_width_ = min_width; } - // The following methods returns pointer to a shared instance of the SkBitmap. - // This shared bitmap is owned by the resource bundle and should not be freed. - - // Returns the Icon for a network strength for a WifiNetwork |wifi|. - // Expected to never return NULL. - static const SkBitmap* IconForNetworkStrength(const WifiNetwork* wifi); - // Returns the Icon for a network strength for CellularNetwork |cellular|. - // Expected to never return NULL. - static const SkBitmap* IconForNetworkStrength( - const CellularNetwork* cellular); - // Returns the Icon for animating network connecting. - // |animation_value| is the value from Animation.GetCurrentValue() - // |type| is the connection type - // Expected to never return NULL. - static const SkBitmap* IconForNetworkConnecting(double animation_value, - ConnectionType type); - - // Returns the Badge for a given network technology. - // This returns different colored symbols depending on cellular data left. - // Returns NULL if not badge is needed. - static const SkBitmap* BadgeForNetworkTechnology( - const CellularNetwork* cellular); - // Returns the Badge for a given network roaming status. - // This returns "R" badge if network is in roaming state, otherwise - // returns NULL. Badge is supposed to be shown on top right of the icon. - static const SkBitmap* BadgeForRoamingStatus(const CellularNetwork* cellular); - // Returns the badge for the given network if it's active with vpn. - // If |network| is not null, will check if it's the active network. - // If |network| is null or if |network| is the active one, the yellow lock - // badge will be returned, otherwise returns null. - // Badge is supposed to be shown on in bottom left corner of the icon. - static const SkBitmap* BadgeForPrivateNetworkStatus(const Network* network); - - // Returns an Icon for a given network. - static SkBitmap IconForNetwork(const Network* network); - // This method will convert the |icon| bitmap to the correct size for display. - // |icon| must be non-NULL. - // If |badge| icon is not NULL, it will be drawn on top of the icon in - // the bottom-right corner. - static SkBitmap IconForDisplay(const SkBitmap* icon, const SkBitmap* badge); - // This method will convert the |icon| bitmap to the correct size for display. - // |icon| must be non-NULL. - // If one of the |bottom_right_badge| or |top_left_badge| or - // |bottom_left_badge| icons are not NULL, they will be drawn on top of the - // icon. - static SkBitmap IconForDisplay(const SkBitmap* icon, - const SkBitmap* bottom_right_badge, - const SkBitmap* top_left_badge, - const SkBitmap* bottom_left_badge); - - // Returns the connection type which should be passed to subsequent calls - // to IconForNetworkConnecting(). If |network| is non NULL this will be the - // either TYPE_WIFI or TYPE_CELLULAR depending on the network. If |network| - // is NULL it will be the type of a connecting network, preferring TYPE_WIFI - // if both types are connecting. If no network is connecting and |network| is - // NULL, TYPE_WIFI will be returned. - static ConnectionType TypeForNetwork(const Network* network); - private: friend class NetworkMenuModel; @@ -172,7 +114,6 @@ class NetworkMenu { // The network menu. scoped_ptr<views::MenuItemView> menu_item_view_; - scoped_ptr<NetworkMenuModel> main_menu_model_; // Holds minimum width of the menu. diff --git a/chrome/browser/chromeos/status/network_menu_button.cc b/chrome/browser/chromeos/status/network_menu_button.cc index 560b68f..1fff569 100644 --- a/chrome/browser/chromeos/status/network_menu_button.cc +++ b/chrome/browser/chromeos/status/network_menu_button.cc @@ -28,7 +28,6 @@ #include "grit/theme_resources.h" #include "ui/base/l10n/l10n_util.h" #include "ui/base/resource/resource_bundle.h" -#include "ui/gfx/canvas_skia.h" #include "views/widget/widget.h" namespace { @@ -39,8 +38,6 @@ const int kPromoShowDelayMs = 10000; const int kNotificationCountPrefDefault = -1; -const int kThrobDuration = 750; - bool GetBooleanPref(const char* pref_name) { Browser* browser = BrowserList::GetLastActive(); // Default to safe value which is false (not to show bubble). @@ -99,21 +96,16 @@ namespace chromeos { NetworkMenuButton::NetworkMenuButton(StatusAreaHost* host) : StatusAreaButton(host, this), - icon_(NULL), - right_badge_(NULL), - top_left_badge_(NULL), - left_badge_(NULL), mobile_data_bubble_(NULL), is_browser_mode_(false), check_for_promo_(true), was_sim_locked_(false), - ALLOW_THIS_IN_INITIALIZER_LIST(animation_connecting_(this)), - ALLOW_THIS_IN_INITIALIZER_LIST(method_factory_(this)), - last_network_type_(TYPE_WIFI) { + ALLOW_THIS_IN_INITIALIZER_LIST(method_factory_(this)) { is_browser_mode_ = (host->GetScreenMode() == StatusAreaHost::kBrowserMode); network_menu_.reset(new NetworkMenu(this, is_browser_mode_)); - animation_connecting_.SetThrobDuration(kThrobDuration); - animation_connecting_.SetTweenType(ui::Tween::LINEAR); + network_icon_.reset( + new NetworkMenuIcon(this, NetworkMenuIcon::MENU_MODE)); + NetworkLibrary* network_library = CrosLibrary::Get()->GetNetworkLibrary(); OnNetworkManagerChanged(network_library); network_library->AddNetworkManagerObserver(this); @@ -144,26 +136,13 @@ void NetworkMenuButton::RegisterPrefs(PrefService* local_state) { } //////////////////////////////////////////////////////////////////////////////// -// NetworkMenuButton, ui::AnimationDelegate implementation: - -void NetworkMenuButton::AnimationProgressed(const ui::Animation* animation) { - if (animation == &animation_connecting_) { - SetIconOnly(NetworkMenu::IconForNetworkConnecting( - animation_connecting_.GetCurrentValue(), last_network_type_)); - // No need to set the badge here, because it should already be set. - SchedulePaint(); - } else { - MenuButton::AnimationProgressed(animation); - } -} - -//////////////////////////////////////////////////////////////////////////////// // NetworkLibrary::NetworkDeviceObserver implementation: void NetworkMenuButton::OnNetworkDeviceChanged(NetworkLibrary* cros, const NetworkDevice* device) { // Device status, such as SIMLock may have changed. - OnNetworkChanged(cros, cros->active_network()); + SetNetworkIcon(); + network_menu_->UpdateMenu(); const NetworkDevice* cellular = cros->FindCellularDevice(); if (cellular) { // We make an assumption (which is valid for now) that the SIM @@ -182,7 +161,12 @@ void NetworkMenuButton::OnNetworkDeviceChanged(NetworkLibrary* cros, // NetworkMenuButton, NetworkLibrary::NetworkManagerObserver implementation: void NetworkMenuButton::OnNetworkManagerChanged(NetworkLibrary* cros) { - OnNetworkChanged(cros, cros->active_network()); + // This gets called on initialization, so any changes should be reflected + // in CrosMock::SetNetworkLibraryStatusAreaExpectations(). + SetNetworkIcon(); + network_menu_->UpdateMenu(); + RefreshNetworkObserver(cros); + RefreshNetworkDeviceObserver(cros); ShowOptionalMobileDataPromoNotification(cros); } @@ -190,18 +174,14 @@ void NetworkMenuButton::OnNetworkManagerChanged(NetworkLibrary* cros) { // NetworkMenuButton, NetworkLibrary::NetworkObserver implementation: void NetworkMenuButton::OnNetworkChanged(NetworkLibrary* cros, const Network* network) { - // This gets called on initialization, so any changes should be reflected - // in CrosMock::SetNetworkLibraryStatusAreaExpectations(). - SetNetworkIcon(cros, network); - RefreshNetworkObserver(cros); - RefreshNetworkDeviceObserver(cros); - SchedulePaint(); + SetNetworkIcon(); network_menu_->UpdateMenu(); } void NetworkMenuButton::OnCellularDataPlanChanged(NetworkLibrary* cros) { // Call OnNetworkManagerChanged which will update the icon. - OnNetworkManagerChanged(cros); + SetNetworkIcon(); + network_menu_->UpdateMenu(); } //////////////////////////////////////////////////////////////////////////////// @@ -227,8 +207,8 @@ bool NetworkMenuButton::ShouldOpenButtonOptions() const { // NetworkMenuButton, views::View implementation: void NetworkMenuButton::OnLocaleChanged() { - NetworkLibrary* lib = CrosLibrary::Get()->GetNetworkLibrary(); - SetNetworkIcon(lib, lib->active_network()); + SetNetworkIcon(); + network_menu_->UpdateMenu(); } //////////////////////////////////////////////////////////////////////////////// @@ -238,6 +218,14 @@ void NetworkMenuButton::RunMenu(views::View* source, const gfx::Point& pt) { } //////////////////////////////////////////////////////////////////////////////// +// NetworkMenuButton, NetworkMenuIcon::Delegate implementation: +void NetworkMenuButton::NetworkMenuIconChanged() { + const SkBitmap* bitmap = network_icon_->GetIconAndText(NULL); + SetIcon(*bitmap); + SchedulePaint(); +} + +//////////////////////////////////////////////////////////////////////////////// // MessageBubbleDelegate implementation: void NetworkMenuButton::BubbleClosing(Bubble* bubble, bool closed_by_escape) { @@ -287,7 +275,7 @@ void NetworkMenuButton::OnLinkActivated(size_t index) { } //////////////////////////////////////////////////////////////////////////////// -// NetworkMenuButton, private methods +// NetworkMenuButton, private methods: const ServicesCustomizationDocument::CarrierDeal* NetworkMenuButton::GetCarrierDeal( @@ -319,125 +307,12 @@ NetworkMenuButton::GetCarrierDeal( return deal; } -void NetworkMenuButton::SetIconAndBadges(const SkBitmap* icon, - const SkBitmap* right_badge, - const SkBitmap* top_left_badge, - const SkBitmap* left_badge) { - icon_ = icon; - right_badge_ = right_badge; - top_left_badge_ = top_left_badge; - left_badge_ = left_badge; - SetIcon(NetworkMenu::IconForDisplay( - icon_, right_badge_, top_left_badge_, left_badge_)); -} - -void NetworkMenuButton::SetIconOnly(const SkBitmap* icon) { - icon_ = icon; - SetIcon(NetworkMenu::IconForDisplay( - icon_, right_badge_, top_left_badge_, left_badge_)); -} - -void NetworkMenuButton::SetBadgesOnly(const SkBitmap* right_badge, - const SkBitmap* top_left_badge, - const SkBitmap* left_badge) { - right_badge_ = right_badge; - top_left_badge_ = top_left_badge; - left_badge_ = left_badge; - SetIcon(NetworkMenu::IconForDisplay( - icon_, right_badge_, top_left_badge_, left_badge_)); -} - -void NetworkMenuButton::SetNetworkIcon(NetworkLibrary* cros, - const Network* network) { - ResourceBundle& rb = ResourceBundle::GetSharedInstance(); - - if (!cros || !CrosLibrary::Get()->EnsureLoaded()) { - SetIconAndBadges(rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_BARS0), - rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_WARNING), - NULL, NULL); - SetTooltipAndAccessibleName( - l10n_util::GetStringUTF16(IDS_STATUSBAR_NETWORK_NO_NETWORK_TOOLTIP)); - return; - } - - if (!cros->Connected() && !cros->Connecting()) { - animation_connecting_.Stop(); - if (last_network_type_ == TYPE_WIFI) { - SetIconAndBadges( - rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_ARCS0), NULL, NULL, NULL); - } else { - SetIconAndBadges( - rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_BARS0), - rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_DISCONNECTED), - NULL, NULL); - } - SetTooltipAndAccessibleName( - l10n_util::GetStringUTF16(IDS_STATUSBAR_NETWORK_NO_NETWORK_TOOLTIP)); - return; - } - - // Stash last network type away so we can show the right icon if we lose - // signal. - last_network_type_ = NetworkMenu::TypeForNetwork(network); - if (cros->wifi_connecting() || cros->cellular_connecting()) { - // Start the connecting animation if not running. - if (!animation_connecting_.is_animating()) { - animation_connecting_.Reset(); - animation_connecting_.StartThrobbing(-1); - SetIconOnly(NetworkMenu::IconForNetworkConnecting(0, last_network_type_)); - } - const WirelessNetwork* wireless = NULL; - if (cros->wifi_connecting()) { - wireless = cros->wifi_network(); - SetBadgesOnly(NULL, NULL, NULL); - } else { // cellular_connecting - wireless = cros->cellular_network(); - SetBadgesOnly( - NetworkMenu::BadgeForNetworkTechnology(cros->cellular_network()), - NetworkMenu::BadgeForRoamingStatus(cros->cellular_network()), - NULL); - } - SetTooltipAndAccessibleName(l10n_util::GetStringFUTF16( - wireless->configuring() ? IDS_STATUSBAR_NETWORK_CONFIGURING_TOOLTIP - : IDS_STATUSBAR_NETWORK_CONNECTING_TOOLTIP, - UTF8ToUTF16(wireless->name()))); - } else { - // Stop connecting animation since we are not connecting. - animation_connecting_.Stop(); - // Only set the icon, if it is an active network that changed. - if (network && network->is_active()) { - const SkBitmap* right_badge(NULL); - const SkBitmap* top_left_badge(NULL); - const SkBitmap* left_badge(NULL); - if (cros->virtual_network()) - left_badge = rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_SECURE); - if (network->type() == TYPE_ETHERNET) { - SetIconAndBadges(rb.GetBitmapNamed(IDR_STATUSBAR_WIRED), - right_badge, top_left_badge, left_badge); - SetTooltipAndAccessibleName(l10n_util::GetStringFUTF16( - IDS_STATUSBAR_NETWORK_CONNECTED_TOOLTIP, - l10n_util::GetStringUTF16( - IDS_STATUSBAR_NETWORK_DEVICE_ETHERNET))); - } else if (network->type() == TYPE_WIFI) { - const WifiNetwork* wifi = static_cast<const WifiNetwork*>(network); - SetIconAndBadges(NetworkMenu::IconForNetworkStrength(wifi), - right_badge, top_left_badge, left_badge); - SetTooltipAndAccessibleName(l10n_util::GetStringFUTF16( - IDS_STATUSBAR_NETWORK_CONNECTED_TOOLTIP, - UTF8ToUTF16(wifi->name()))); - } else if (network->type() == TYPE_CELLULAR) { - const CellularNetwork* cellular = - static_cast<const CellularNetwork*>(network); - right_badge = NetworkMenu::BadgeForNetworkTechnology(cellular); - top_left_badge = NetworkMenu::BadgeForRoamingStatus(cellular); - SetIconAndBadges(NetworkMenu::IconForNetworkStrength(cellular), - right_badge, top_left_badge, left_badge); - SetTooltipAndAccessibleName(l10n_util::GetStringFUTF16( - IDS_STATUSBAR_NETWORK_CONNECTED_TOOLTIP, - UTF8ToUTF16(cellular->name()))); - } - } - } +void NetworkMenuButton::SetNetworkIcon() { + string16 tooltip; + const SkBitmap* bitmap = network_icon_->GetIconAndText(&tooltip); + SetIcon(*bitmap); + SetTooltipAndAccessibleName(tooltip); + SchedulePaint(); } void NetworkMenuButton::RefreshNetworkObserver(NetworkLibrary* cros) { diff --git a/chrome/browser/chromeos/status/network_menu_button.h b/chrome/browser/chromeos/status/network_menu_button.h index 3604738..fd96dc9 100644 --- a/chrome/browser/chromeos/status/network_menu_button.h +++ b/chrome/browser/chromeos/status/network_menu_button.h @@ -14,8 +14,8 @@ #include "chrome/browser/chromeos/customization_document.h" #include "chrome/browser/chromeos/login/message_bubble.h" #include "chrome/browser/chromeos/status/network_menu.h" +#include "chrome/browser/chromeos/status/network_menu_icon.h" #include "chrome/browser/chromeos/status/status_area_button.h" -#include "ui/base/animation/throb_animation.h" class PrefService; @@ -54,6 +54,7 @@ class StatusAreaHost; class NetworkMenuButton : public StatusAreaButton, public views::ViewMenuDelegate, public NetworkMenu::Delegate, + public NetworkMenuIcon::Delegate, public NetworkLibrary::NetworkDeviceObserver, public NetworkLibrary::NetworkManagerObserver, public NetworkLibrary::NetworkObserver, @@ -65,36 +66,40 @@ class NetworkMenuButton : public StatusAreaButton, static void RegisterPrefs(PrefService* local_state); - // ui::AnimationDelegate implementation. - virtual void AnimationProgressed(const ui::Animation* animation); - // NetworkLibrary::NetworkDeviceObserver implementation. virtual void OnNetworkDeviceChanged(NetworkLibrary* cros, - const NetworkDevice* device); + const NetworkDevice* device) OVERRIDE; + // NetworkLibrary::NetworkManagerObserver implementation. - virtual void OnNetworkManagerChanged(NetworkLibrary* cros); + virtual void OnNetworkManagerChanged(NetworkLibrary* cros) OVERRIDE; + // NetworkLibrary::NetworkObserver implementation. - virtual void OnNetworkChanged(NetworkLibrary* cros, const Network* network); + virtual void OnNetworkChanged(NetworkLibrary* cros, + const Network* network) OVERRIDE; + // NetworkLibrary::CellularDataPlanObserver implementation. - virtual void OnCellularDataPlanChanged(NetworkLibrary* cros); + virtual void OnCellularDataPlanChanged(NetworkLibrary* cros) OVERRIDE; // NetworkMenu::Delegate implementation: - virtual views::MenuButton* GetMenuButton(); - virtual gfx::NativeWindow GetNativeWindow() const; - virtual void OpenButtonOptions(); - virtual bool ShouldOpenButtonOptions() const; + virtual views::MenuButton* GetMenuButton() OVERRIDE; + virtual gfx::NativeWindow GetNativeWindow() const OVERRIDE; + virtual void OpenButtonOptions() OVERRIDE; + virtual bool ShouldOpenButtonOptions() const OVERRIDE; + + // NetworkMenuIcon::Delegate implementation: + virtual void NetworkMenuIconChanged() OVERRIDE; // views::View virtual void OnLocaleChanged() OVERRIDE; // views::ViewMenuDelegate implementation. - virtual void RunMenu(views::View* source, const gfx::Point& pt); + virtual void RunMenu(views::View* source, const gfx::Point& pt) OVERRIDE; // MessageBubbleDelegate implementation: - virtual void BubbleClosing(Bubble* bubble, bool closed_by_escape); - virtual bool CloseOnEscape(); - virtual bool FadeInOnShow(); - virtual void OnLinkActivated(size_t index); + virtual void BubbleClosing(Bubble* bubble, bool closed_by_escape) OVERRIDE; + virtual bool CloseOnEscape() OVERRIDE; + virtual bool FadeInOnShow() OVERRIDE; + virtual void OnLinkActivated(size_t index) OVERRIDE; private: // Returns carrier deal if it's specified and should be shown, @@ -102,19 +107,8 @@ class NetworkMenuButton : public StatusAreaButton, const ServicesCustomizationDocument::CarrierDeal* GetCarrierDeal( NetworkLibrary* cros); - // Sets the icon and the badges (badges are at the bottom of the icon). - void SetIconAndBadges(const SkBitmap* icon, - const SkBitmap* right_badge, - const SkBitmap* top_left_badge, - const SkBitmap* left_badge); - // Sets the icon only. Keep the previous badge. - void SetIconOnly(const SkBitmap* icon); - // Sets the badges only. Keep the previous icon. - void SetBadgesOnly(const SkBitmap* right_badge, - const SkBitmap* top_left_badge, - const SkBitmap* left_badge); // Set the network icon based on the status of the |network| - void SetNetworkIcon(NetworkLibrary* cros, const Network* network); + void SetNetworkIcon(); // Called when the list of devices has possibly changed. This will remove // old network device observers and add a network observers @@ -136,14 +130,8 @@ class NetworkMenuButton : public StatusAreaButton, // Path of the Cellular device that we monitor property updates from. std::string cellular_device_path_; - // The icon showing the network strength. - const SkBitmap* icon_; - // A badge icon displayed on top of icon, in bottom-right corner. - const SkBitmap* right_badge_; - // A badge icon displayed on top of icon, in top-left corner. - const SkBitmap* top_left_badge_; - // A badge icon displayed on top of icon, in bottom-left corner. - const SkBitmap* left_badge_; + // The network icon and associated data. + scoped_ptr<NetworkMenuIcon> network_icon_; // Notification bubble for 3G promo. MessageBubble* mobile_data_bubble_; @@ -158,9 +146,6 @@ class NetworkMenuButton : public StatusAreaButton, // Cellular device SIM was locked when we last checked bool was_sim_locked_; - // The throb animation that does the wifi connecting animation. - ui::ThrobAnimation animation_connecting_; - // If any network is currently active, this is the service path of the one // whose status is displayed in the network menu button. std::string active_network_; @@ -174,9 +159,6 @@ class NetworkMenuButton : public StatusAreaButton, // Factory for delaying showing promo notification. ScopedRunnableMethodFactory<NetworkMenuButton> method_factory_; - // The last network we connected to (or tried to). - ConnectionType last_network_type_; - DISALLOW_COPY_AND_ASSIGN(NetworkMenuButton); }; diff --git a/chrome/browser/chromeos/status/network_menu_icon.cc b/chrome/browser/chromeos/status/network_menu_icon.cc new file mode 100644 index 0000000..e33634e --- /dev/null +++ b/chrome/browser/chromeos/status/network_menu_icon.cc @@ -0,0 +1,682 @@ +// Copyright (c) 2011 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "chrome/browser/chromeos/status/network_menu_icon.h" + +#include <math.h> + +#include "base/utf_string_conversions.h" +#include "chrome/browser/chromeos/cros/cros_library.h" +#include "grit/generated_resources.h" +#include "grit/theme_resources.h" +#include "ui/base/l10n/l10n_util.h" +#include "ui/base/resource/resource_bundle.h" +#include "ui/gfx/canvas_skia.h" +#include "ui/gfx/skbitmap_operations.h" + +namespace chromeos { + +namespace { + +// Amount to fade icons while connecting. +const double kConnectingImageAlpha = 0.5; + +// Animation cycle length. +const int kThrobDurationMs = 750; + +// Network strength bars images. +const int kNumBarsImages = 4; + +// NOTE: Use an array rather than just calculating a resource number to avoid +// creating implicit ordering dependencies on the resource values. +const int kBarsImages[kNumBarsImages + 1] = { + IDR_STATUSBAR_NETWORK_BARS0, + IDR_STATUSBAR_NETWORK_BARS1, + IDR_STATUSBAR_NETWORK_BARS2, + IDR_STATUSBAR_NETWORK_BARS3, + IDR_STATUSBAR_NETWORK_BARS4, +}; + +// Animation does not include BARS0. +SkBitmap kBarsImagesAnimating[kNumBarsImages]; + +// Network strength arcs images. +const int kNumArcsImages = 7; + +// NOTE: Use an array rather than just calculating a resource number to avoid +// creating implicit ordering dependencies on the resource values. +const int kArcsImages[kNumArcsImages + 1] = { + IDR_STATUSBAR_NETWORK_ARCS0, + IDR_STATUSBAR_NETWORK_ARCS1, + IDR_STATUSBAR_NETWORK_ARCS2, + IDR_STATUSBAR_NETWORK_ARCS3, + IDR_STATUSBAR_NETWORK_ARCS4, + IDR_STATUSBAR_NETWORK_ARCS5, + IDR_STATUSBAR_NETWORK_ARCS6, + IDR_STATUSBAR_NETWORK_ARCS7, +}; + +// Animation does not include BARS0. +SkBitmap kArcsImagesAnimating[kNumArcsImages]; + +// Badge offsets. +const int kBadgeLeftX = 0; +const int kBadgeRightX = 14; +const int kBadgeTopY = 0; +const int kBadgeBottomY = 14; + +// ID for VPN badge. TODO(stevenjb): replace with yellow lock icon. +const int kVpnBadgeId = IDR_STATUSBAR_NETWORK_SECURE; + +int StrengthIndex(int strength, int count) { + if (strength == 0) { + return 0; + } else { + // Return an index in the range [1, count]. + float findex = (static_cast<float>(strength) / 100.0f) * + nextafter(static_cast<float>(count), 0); + int index = 1 + static_cast<int>(findex); + index = std::max(std::min(index, count), 1); + return index; + } +} + +int WifiStrengthIndex(const WifiNetwork* wifi) { + return StrengthIndex(wifi->strength(), kNumArcsImages); +} + +int CellularStrengthIndex(const CellularNetwork* cellular) { + if (cellular->data_left() == CellularNetwork::DATA_NONE) + return 0; + else + return StrengthIndex(cellular->strength(), kNumBarsImages); +} + +const SkBitmap* BadgeForNetworkTechnology(const CellularNetwork* cellular) { + int id = -1; + switch (cellular->network_technology()) { + case NETWORK_TECHNOLOGY_EVDO: + switch (cellular->data_left()) { + case CellularNetwork::DATA_NONE: + id = IDR_STATUSBAR_NETWORK_3G_ERROR; + break; + case CellularNetwork::DATA_VERY_LOW: + case CellularNetwork::DATA_LOW: + case CellularNetwork::DATA_NORMAL: + id = IDR_STATUSBAR_NETWORK_3G; + break; + case CellularNetwork::DATA_UNKNOWN: + id = IDR_STATUSBAR_NETWORK_3G_UNKNOWN; + break; + } + break; + case NETWORK_TECHNOLOGY_1XRTT: + switch (cellular->data_left()) { + case CellularNetwork::DATA_NONE: + id = IDR_STATUSBAR_NETWORK_1X_ERROR; + break; + case CellularNetwork::DATA_VERY_LOW: + case CellularNetwork::DATA_LOW: + case CellularNetwork::DATA_NORMAL: + id = IDR_STATUSBAR_NETWORK_1X; + break; + case CellularNetwork::DATA_UNKNOWN: + id = IDR_STATUSBAR_NETWORK_1X_UNKNOWN; + break; + } + break; + // Note: we may not be able to obtain data usage info from GSM carriers, + // so there may not be a reason to create _ERROR or _UNKNOWN versions + // of the following icons. + case NETWORK_TECHNOLOGY_GPRS: + id = IDR_STATUSBAR_NETWORK_GPRS; + break; + case NETWORK_TECHNOLOGY_EDGE: + id = IDR_STATUSBAR_NETWORK_EDGE; + break; + case NETWORK_TECHNOLOGY_UMTS: + id = IDR_STATUSBAR_NETWORK_3G; + break; + case NETWORK_TECHNOLOGY_HSPA: + id = IDR_STATUSBAR_NETWORK_HSPA; + break; + case NETWORK_TECHNOLOGY_HSPA_PLUS: + id = IDR_STATUSBAR_NETWORK_HSPA_PLUS; + break; + case NETWORK_TECHNOLOGY_LTE: + id = IDR_STATUSBAR_NETWORK_LTE; + break; + case NETWORK_TECHNOLOGY_LTE_ADVANCED: + id = IDR_STATUSBAR_NETWORK_LTE_ADVANCED; + break; + case NETWORK_TECHNOLOGY_GSM: + id = IDR_STATUSBAR_NETWORK_GPRS; + break; + case NETWORK_TECHNOLOGY_UNKNOWN: + break; + } + if (id == -1) + return NULL; + else + return ResourceBundle::GetSharedInstance().GetBitmapNamed(id); +} + +} // namespace + +//////////////////////////////////////////////////////////////////////////////// +// NetworkIcon + +// Sets up and generates an SkBitmap for a Network icon. +class NetworkIcon { + public: + NetworkIcon() + : state_(STATE_UNKNOWN), + strength_index_(-1), + icon_(NULL), + top_left_badge_(NULL), + top_right_badge_(NULL), + bottom_left_badge_(NULL), + bottom_right_badge_(NULL) { + } + + explicit NetworkIcon(const std::string& service_path) + : service_path_(service_path), + state_(STATE_UNKNOWN), + strength_index_(-1), + icon_(NULL), + top_left_badge_(NULL), + top_right_badge_(NULL), + bottom_left_badge_(NULL), + bottom_right_badge_(NULL) { + } + + ~NetworkIcon() { + } + + void ClearIconAndBadges() { + icon_ = NULL; + top_left_badge_ = NULL; + top_right_badge_ = NULL; + bottom_left_badge_ = NULL; + bottom_right_badge_ = NULL; + } + + void SetDirty() { + state_ = STATE_UNKNOWN; + strength_index_ = -1; + } + + // 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() { + chromeos::NetworkLibrary* cros = + chromeos::CrosLibrary::Get()->GetNetworkLibrary(); + // First look for a visible network. + const Network* network = cros->FindNetworkByPath(service_path_); + if (!network) { + // If not a visible network, check for a remembered network. + network = cros->FindRememberedNetworkByPath(service_path_); + if (!network) + return; + } + bool dirty = bitmap_.empty(); + if (state_ != network->state()) { + state_ = network->state(); + dirty = true; + } + ConnectionType type = network->type(); + if (type == TYPE_WIFI || type == TYPE_CELLULAR) { + int index = 0; + if (type == TYPE_WIFI) { + index = WifiStrengthIndex( + static_cast<const WifiNetwork*>(network)); + } else if (type == TYPE_CELLULAR) { + index = CellularStrengthIndex( + static_cast<const CellularNetwork*>(network)); + } + if (index != strength_index_) { + strength_index_ = index; + dirty = true; + } + } + if (dirty) { + UpdateIcon(network); + GenerateBitmap(); + } + } + + // Sets up the base icon image. + void SetIcon(const Network* network) { + ResourceBundle& rb = ResourceBundle::GetSharedInstance(); + + switch (network->type()) { + case TYPE_ETHERNET: { + icon_ = rb.GetBitmapNamed(IDR_STATUSBAR_WIRED); + break; + } + case TYPE_WIFI: { + const WifiNetwork* wifi = + static_cast<const WifiNetwork*>(network); + if (strength_index_ == -1) + strength_index_ = WifiStrengthIndex(wifi); + icon_ = rb.GetBitmapNamed(kArcsImages[strength_index_]); + break; + } + case TYPE_CELLULAR: { + const CellularNetwork* cellular = + static_cast<const CellularNetwork*>(network); + if (strength_index_ == -1) + strength_index_ = CellularStrengthIndex(cellular); + icon_ = rb.GetBitmapNamed(kBarsImages[strength_index_]); + break; + } + default: { + LOG(WARNING) << "Request for icon for unsupported type: " + << network->type(); + icon_ = rb.GetBitmapNamed(IDR_STATUSBAR_WIRED); + break; + } + } + } + + // Sets up the various badges: + // top_left: Cellular Roaming + // top_right: Unused + // bottom_left: VPN + // bottom_right: disconnected / secure / technology / warning + void SetBadges(const Network* network) { + ResourceBundle& rb = ResourceBundle::GetSharedInstance(); + + switch (network->type()) { + case TYPE_ETHERNET: { + if (network->disconnected()) { + bottom_right_badge_ = + rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_DISCONNECTED); + } + break; + } + case TYPE_WIFI: { + const WifiNetwork* wifi = + static_cast<const WifiNetwork*>(network); + if (wifi->encrypted()) + bottom_right_badge_ = rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_SECURE); + break; + } + case TYPE_CELLULAR: { + const CellularNetwork* cellular = + static_cast<const CellularNetwork*>(network); + if (cellular->roaming_state() == ROAMING_STATE_ROAMING) + top_left_badge_ = rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_ROAMING); + if (!cellular->connecting()) + bottom_right_badge_ = BadgeForNetworkTechnology(cellular); + break; + } + default: + break; + } + } + + // Clears any previous state then sets the base icon and badges. + void UpdateIcon(const Network* network) { + ResourceBundle& rb = ResourceBundle::GetSharedInstance(); + chromeos::NetworkLibrary* cros = + chromeos::CrosLibrary::Get()->GetNetworkLibrary(); + + ClearIconAndBadges(); + + if (network->type() == TYPE_VPN) { + // VPN should never be the primiary active network. This is used for + // the icon next to a connected or disconnected VPN. + const Network* connected_network = cros->connected_network(); + if (connected_network && connected_network->type() != TYPE_VPN) { + // Set the icon and badges for the connected network. + SetIcon(connected_network); + SetBadges(connected_network); + } else { + // Use the ethernet icon for VPN when not connected. + icon_ = rb.GetBitmapNamed(IDR_STATUSBAR_WIRED); + } + // Overlay the VPN badge. + bottom_left_badge_ = rb.GetBitmapNamed(kVpnBadgeId); + } else { + SetIcon(network); + SetBadges(network); + } + } + + // Generates the bitmap. Call after setting the icon and badges. + void GenerateBitmap() { + if (!icon_) + return; + + gfx::CanvasSkia canvas(icon_->width(), icon_->height(), false); + canvas.DrawBitmapInt(*icon_, 0, 0); + + if (top_left_badge_) { + canvas.DrawBitmapInt( + *top_left_badge_, kBadgeLeftX, kBadgeTopY); + } + if (top_right_badge_) { + canvas.DrawBitmapInt( + *top_right_badge_, kBadgeRightX, kBadgeTopY); + } + if (bottom_left_badge_) { + canvas.DrawBitmapInt( + *bottom_left_badge_, kBadgeLeftX, kBadgeBottomY); + } + if (bottom_right_badge_) { + canvas.DrawBitmapInt( + *bottom_right_badge_, kBadgeRightX, kBadgeBottomY); + } + + bitmap_ = canvas.ExtractBitmap(); + } + + const SkBitmap* GetBitmap() const { return &bitmap_; } + + void set_icon(const SkBitmap* icon) { icon_ = icon; } + void set_top_left_badge(const SkBitmap* badge) { + top_left_badge_ = badge; + } + void set_top_right_badge(const SkBitmap* badge) { + top_right_badge_ = badge; + } + void set_bottom_left_badge(const SkBitmap* badge) { + bottom_left_badge_ = badge; + } + void set_bottom_right_badge(const SkBitmap* badge) { + bottom_right_badge_ = badge; + } + + private: + std::string service_path_; + ConnectionState state_; + int strength_index_; + SkBitmap bitmap_; + const SkBitmap* icon_; + const SkBitmap* top_left_badge_; + const SkBitmap* top_right_badge_; + const SkBitmap* bottom_left_badge_; + const SkBitmap* bottom_right_badge_; + + DISALLOW_COPY_AND_ASSIGN(NetworkIcon); +}; + + +//////////////////////////////////////////////////////////////////////////////// +// NetworkMenuIcon + +NetworkMenuIcon::NetworkMenuIcon(Delegate* delegate, Mode mode) + : mode_(mode), + delegate_(delegate), + ALLOW_THIS_IN_INITIALIZER_LIST(animation_connecting_(this)), + last_network_type_(TYPE_WIFI) { + // Generate empty images for blending. + ResourceBundle& rb = ResourceBundle::GetSharedInstance(); + const SkBitmap* source_badge = rb.GetBitmapNamed(kArcsImages[0]); + empty_badge_.setConfig(SkBitmap::kARGB_8888_Config, + source_badge->width(), source_badge->height(), 0); + empty_badge_.allocPixels(); + empty_badge_.eraseARGB(0, 0, 0, 0); + const SkBitmap* vpn_badge = rb.GetBitmapNamed(kVpnBadgeId); + empty_vpn_badge_.setConfig(SkBitmap::kARGB_8888_Config, + vpn_badge->width(), vpn_badge->height(), 0); + empty_vpn_badge_.allocPixels(); + empty_vpn_badge_.eraseARGB(0, 0, 0, 0); + + // Set up the connection animation throbber. + animation_connecting_.SetThrobDuration(kThrobDurationMs); + animation_connecting_.SetTweenType(ui::Tween::LINEAR); + + // Initialize the icon. + icon_.reset(new NetworkIcon()); +} + +NetworkMenuIcon::~NetworkMenuIcon() { +} + +// Public methods: + +const SkBitmap* NetworkMenuIcon::GetIconAndText(string16* text) { + SetIconAndText(text); + icon_->GenerateBitmap(); + return icon_->GetBitmap(); +} + +// ui::AnimationDelegate: +void NetworkMenuIcon::AnimationProgressed(const ui::Animation* animation) { + if (animation == &animation_connecting_ && delegate_) { + // Only update the connecting network from here. + if (GetConnectingNetwork() == connecting_network_) + delegate_->NetworkMenuIconChanged(); + } +} + +// Private methods: + +// In menu mode, returns any connecting network. +// In dropdown mode, only returns connecting network if not connected. +const Network* NetworkMenuIcon::GetConnectingNetwork() { + NetworkLibrary* cros = CrosLibrary::Get()->GetNetworkLibrary(); + if ((mode_ == MENU_MODE) || + (mode_ == DROPDOWN_MODE && !cros->connected_network())) { + const Network* connecting_network = cros->connecting_network(); + // Only show connecting icon for wireless networks. + if (connecting_network && connecting_network->type() != TYPE_ETHERNET) { + return connecting_network; + } + } + return NULL; +} + +// Starts the connection animation if necessary and returns its current value. +double NetworkMenuIcon::GetAnimation() { + if (!animation_connecting_.is_animating()) { + animation_connecting_.Reset(); + animation_connecting_.StartThrobbing(-1); + return 0; + } + return animation_connecting_.GetCurrentValue(); +} + +// Fades the bars a bit and cycles through the different bar states. +void NetworkMenuIcon::SetConnectingIcon(const Network* network, + double animation) { + int image_count; + const int* source_image_ids; + SkBitmap* images; + + if (network->type() == TYPE_WIFI) { + image_count = kNumArcsImages; + source_image_ids = kArcsImages; + images = kArcsImagesAnimating; + } else { + image_count = kNumBarsImages; + source_image_ids = kBarsImages; + images = kBarsImagesAnimating; + } + int index = static_cast<int>( + animation * nextafter(static_cast<float>(image_count), 0)); + index = std::max(std::min(index, image_count - 1), 0); + + // Lazily cache images. + if (images[index].empty()) { + ResourceBundle& rb = ResourceBundle::GetSharedInstance(); + SkBitmap* source = rb.GetBitmapNamed(source_image_ids[1 + index]); + images[index] = SkBitmapOperations::CreateBlendedBitmap( + empty_badge_, *source, kConnectingImageAlpha); + } + icon_->set_icon(&images[index]); +} + +// Sets up the icon and badges for GenerateBitmap(). +void NetworkMenuIcon::SetIconAndText(string16* text) { + NetworkLibrary* cros = CrosLibrary::Get()->GetNetworkLibrary(); + ResourceBundle& rb = ResourceBundle::GetSharedInstance(); + + icon_->ClearIconAndBadges(); + + // Display warning badge if cros is not loaded. + if (!cros || !CrosLibrary::Get()->EnsureLoaded()) { + icon_->set_icon(rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_BARS0)); + icon_->set_bottom_right_badge( + rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_WARNING)); + if (text) { + if (mode_ == MENU_MODE) { + *text = l10n_util::GetStringUTF16( + IDS_STATUSBAR_NETWORK_NO_NETWORK_TOOLTIP); + } else { + *text = l10n_util::GetStringUTF16(IDS_STATUSBAR_NO_NETWORKS_MESSAGE); + } + } + return; + } + + // If we are connecting to a network, display that. + connecting_network_ = GetConnectingNetwork(); + if (connecting_network_) { + double animation = GetAnimation(); + SetConnectingIcon(connecting_network_, animation); + icon_->SetBadges(connecting_network_); + if (text) { + if (mode_ == MENU_MODE) { + int tooltip_id = connecting_network_->configuring() + ? IDS_STATUSBAR_NETWORK_CONFIGURING_TOOLTIP + : IDS_STATUSBAR_NETWORK_CONNECTING_TOOLTIP; + *text = l10n_util::GetStringFUTF16( + tooltip_id, UTF8ToUTF16(connecting_network_->name())); + } else { + *text = UTF8ToUTF16(connecting_network_->name()); + } + } + return; + } + + // If we are not connecting to a network, show the active network. + const Network* network = cros->active_network(); + if (network) { + bool animating = false; + last_network_type_ = network->type(); + // Icon + badges. + icon_->SetDirty(); + icon_->UpdateIcon(network); + // Overlay the VPN badge if connected or connecting to a VPN. + if (cros->virtual_network()) { + const SkBitmap* vpn_badge = rb.GetBitmapNamed(kVpnBadgeId); + if (cros->virtual_network()->connecting()) { + double animation = GetAnimation(); + animating = true; + // Even though this is the only place we use vpn_connecting_badge_, + // it is important that this is a member variable since we set a + // pointer to it and access that pointer in icon_->GenerateBitmap(). + vpn_connecting_badge_ = SkBitmapOperations::CreateBlendedBitmap( + empty_vpn_badge_, *vpn_badge, animation); + icon_->set_bottom_left_badge(&vpn_connecting_badge_); + } else if (cros->virtual_network()->connected()) { + icon_->set_bottom_left_badge(vpn_badge); + } + } + if (!animating) + animation_connecting_.Stop(); + // Text. + if (text) { + switch (network->type()) { + case TYPE_ETHERNET: + if (mode_ == MENU_MODE) { + *text = l10n_util::GetStringFUTF16( + IDS_STATUSBAR_NETWORK_CONNECTED_TOOLTIP, + l10n_util::GetStringUTF16( + IDS_STATUSBAR_NETWORK_DEVICE_ETHERNET)); + } else { + *text = l10n_util::GetStringUTF16( + IDS_STATUSBAR_NETWORK_DEVICE_ETHERNET); + } + break; + default: + if (mode_ == MENU_MODE) { + *text = l10n_util::GetStringFUTF16( + IDS_STATUSBAR_NETWORK_CONNECTED_TOOLTIP, + UTF8ToUTF16(network->name())); + } else { + *text = UTF8ToUTF16(network->name()); + } + break; + } + } + return; + } + + // Not connecting, so stop animation. + animation_connecting_.Stop(); + + // No connecting, connected, or active network. + switch (last_network_type_) { + case TYPE_ETHERNET: + icon_->set_icon(rb.GetBitmapNamed(IDR_STATUSBAR_WIRED)); + icon_->set_bottom_right_badge( + rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_DISCONNECTED)); + break; + case TYPE_WIFI: + icon_->set_icon(rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_ARCS0)); + break; + case TYPE_CELLULAR: + default: + icon_->set_icon(rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_BARS0)); + icon_->set_bottom_right_badge( + rb.GetBitmapNamed(IDR_STATUSBAR_NETWORK_DISCONNECTED)); + break; + } + if (text) { + if (mode_ == MENU_MODE) { + *text = l10n_util::GetStringUTF16( + IDS_STATUSBAR_NETWORK_NO_NETWORK_TOOLTIP); + } else { + *text = l10n_util::GetStringUTF16(IDS_NETWORK_SELECTION_NONE); } + } +} + +// Static functions for generating network icon bitmaps: + +// Generatings an icon bitmap for a network's current state. +const SkBitmap* NetworkMenuIcon::GetBitmap(const Network* network) { + DCHECK(network); + // Maintain a static (global) icon map. Note: Icons are never destroyed; + // it is assumed that a finite and reasonable number of network icons will be + // created during a session. + typedef std::map<std::string, NetworkIcon*> NetworkIconMap; + static NetworkIconMap* icon_map = NULL; + if (icon_map == NULL) + icon_map = new NetworkIconMap; + // Find or add the icon. + NetworkIcon* icon; + NetworkIconMap::iterator iter = icon_map->find(network->service_path()); + if (iter == icon_map->end()) { + icon = new NetworkIcon(network->service_path()); + icon_map->insert(std::make_pair(network->service_path(), icon)); + } else { + icon = iter->second; + } + // Update and return the icon's bitmap. + icon->Update(); + return icon->GetBitmap(); +} + +// Returns an icon for a disconnected VPN. +const SkBitmap* NetworkMenuIcon::GetVpnBitmap() { + static SkBitmap* vpn_bitmap = NULL; + if (vpn_bitmap == NULL) { + // Set the disconencted vpn icon (ethernet + VPN) for GetVpnIcon(). + ResourceBundle& rb = ResourceBundle::GetSharedInstance(); + const SkBitmap* ethernet_icon = rb.GetBitmapNamed(IDR_STATUSBAR_WIRED); + gfx::CanvasSkia canvas( + ethernet_icon->width(), ethernet_icon->height(), false); + canvas.DrawBitmapInt(*ethernet_icon, 0, 0); + const SkBitmap* vpn_badge = rb.GetBitmapNamed(kVpnBadgeId); + canvas.DrawBitmapInt(*vpn_badge, kBadgeLeftX, kBadgeBottomY); + vpn_bitmap = new SkBitmap(canvas.ExtractBitmap()); + } + return vpn_bitmap; +} + +} // chromeos diff --git a/chrome/browser/chromeos/status/network_menu_icon.h b/chrome/browser/chromeos/status/network_menu_icon.h new file mode 100644 index 0000000..7171e09 --- /dev/null +++ b/chrome/browser/chromeos/status/network_menu_icon.h @@ -0,0 +1,77 @@ +// Copyright (c) 2011 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef CHROME_BROWSER_CHROMEOS_STATUS_NETWORK_MENU_ICON_H_ +#define CHROME_BROWSER_CHROMEOS_STATUS_NETWORK_MENU_ICON_H_ +#pragma once + +#include <string> +#include <map> + +#include "base/memory/scoped_ptr.h" +#include "chrome/browser/chromeos/cros/network_library.h" +#include "third_party/skia/include/core/SkBitmap.h" +#include "ui/base/animation/animation_delegate.h" +#include "ui/base/animation/throb_animation.h" + +namespace chromeos { + +class NetworkIcon; + +// Manages an icon reflecting the current state of the network. +// Also provides static functions for fetching network bitmaps. +class NetworkMenuIcon : public ui::AnimationDelegate { + public: + enum Mode { + MENU_MODE, // Prioritizes connecting networks and sets tooltips. + DROPDOWN_MODE, // Prioritizes connected networks and sets display text. + }; + + class Delegate { + public: + // Called when the bitmap has changed due to animation. Callback should + // trigger a call to GetIconAndText() to generate and retrieve the bitmap. + virtual void NetworkMenuIconChanged() = 0; + }; + + NetworkMenuIcon(Delegate* delegate, Mode mode); + virtual ~NetworkMenuIcon(); + + // Generates and returns the icon bitmap. This will never return NULL. + // Also sets |text| if not NULL. Behavior varies depending on |mode_|. + const SkBitmap* GetIconAndText(string16* text); + + // ui::AnimationDelegate implementation. + virtual void AnimationProgressed(const ui::Animation* animation); + + // Static functions for generating network icon bitmaps: + + // Returns a bitmap associated with |network|, reflecting its current state. + static const SkBitmap* GetBitmap(const Network* network); + + // Returns a bitmap representing an unconnected VPN. + static const SkBitmap* GetVpnBitmap(); + + private: + double GetAnimation(); + const Network* GetConnectingNetwork(); + void SetConnectingIcon(const Network* network, double animation); + void SetIconAndText(string16* text); + + Mode mode_; + Delegate* delegate_; + SkBitmap empty_badge_; + SkBitmap empty_vpn_badge_; + SkBitmap vpn_connecting_badge_; + ui::ThrobAnimation animation_connecting_; + ConnectionType last_network_type_; + scoped_ptr<NetworkIcon> icon_; + const Network* connecting_network_; // weak pointer. + + DISALLOW_COPY_AND_ASSIGN(NetworkMenuIcon); +}; + +} // namespace chromeos + +#endif // CHROME_BROWSER_CHROMEOS_STATUS_NETWORK_MENU_ICON_H_ diff --git a/chrome/browser/ui/webui/chromeos/mobile_setup_ui.cc b/chrome/browser/ui/webui/chromeos/mobile_setup_ui.cc index ef5f192..79946d7 100644 --- a/chrome/browser/ui/webui/chromeos/mobile_setup_ui.cc +++ b/chrome/browser/ui/webui/chromeos/mobile_setup_ui.cc @@ -753,7 +753,7 @@ void MobileSetupHandler::EvaluateCellularNetwork( case PLAN_ACTIVATION_START: { switch (network->activation_state()) { case chromeos::ACTIVATION_STATE_ACTIVATED: { - if (network->failed_or_disconnected()) { + if (network->disconnected()) { new_state = PLAN_ACTIVATION_RECONNECTING; } else if (network->connected()) { if (network->restricted_pool()) { @@ -765,7 +765,7 @@ void MobileSetupHandler::EvaluateCellularNetwork( break; } default: { - if (network->failed_or_disconnected() || + if (network->disconnected() || network->state() == chromeos::STATE_ACTIVATION_FAILURE) { new_state = (network->activation_state() == chromeos::ACTIVATION_STATE_PARTIALLY_ACTIVATED) ? @@ -783,7 +783,7 @@ void MobileSetupHandler::EvaluateCellularNetwork( case PLAN_ACTIVATION_START_OTASP: { switch (network->activation_state()) { case chromeos::ACTIVATION_STATE_PARTIALLY_ACTIVATED: { - if (network->failed_or_disconnected()) { + if (network->disconnected()) { new_state = PLAN_ACTIVATION_OTASP; } else if (network->connected()) { DisconnectFromNetwork(network); @@ -811,7 +811,7 @@ void MobileSetupHandler::EvaluateCellularNetwork( case PLAN_ACTIVATION_TRYING_OTASP: { switch (network->activation_state()) { case chromeos::ACTIVATION_STATE_ACTIVATED: - if (network->failed_or_disconnected()) { + if (network->disconnected()) { new_state = GetNextReconnectState(state_); } else if (network->connected()) { if (network->restricted_pool()) { diff --git a/chrome/browser/ui/webui/options/chromeos/internet_options_handler.cc b/chrome/browser/ui/webui/options/chromeos/internet_options_handler.cc index 24815d8..2e1e76e 100644 --- a/chrome/browser/ui/webui/options/chromeos/internet_options_handler.cc +++ b/chrome/browser/ui/webui/options/chromeos/internet_options_handler.cc @@ -26,7 +26,7 @@ #include "chrome/browser/chromeos/login/user_manager.h" #include "chrome/browser/chromeos/options/network_config_view.h" #include "chrome/browser/chromeos/sim_dialog_delegate.h" -#include "chrome/browser/chromeos/status/network_menu.h" +#include "chrome/browser/chromeos/status/network_menu_icon.h" #include "chrome/browser/chromeos/user_cros_settings_provider.h" #include "chrome/browser/prefs/pref_service.h" #include "chrome/browser/ui/browser.h" @@ -1030,9 +1030,11 @@ ListValue* InternetOptionsHandler::GetWiredList() { const chromeos::EthernetNetwork* ethernet_network = cros_->ethernet_network(); if (ethernet_network) { + const SkBitmap* icon = + chromeos::NetworkMenuIcon::GetBitmap(ethernet_network); list->Append(GetNetwork( ethernet_network->service_path(), - chromeos::NetworkMenu::IconForNetwork(ethernet_network), + *icon, l10n_util::GetStringUTF8(IDS_STATUSBAR_NETWORK_DEVICE_ETHERNET), ethernet_network->connecting(), ethernet_network->connected(), @@ -1054,9 +1056,10 @@ ListValue* InternetOptionsHandler::GetWirelessList() { const chromeos::WifiNetworkVector& wifi_networks = cros_->wifi_networks(); for (chromeos::WifiNetworkVector::const_iterator it = wifi_networks.begin(); it != wifi_networks.end(); ++it) { + const SkBitmap* icon = chromeos::NetworkMenuIcon::GetBitmap(*it); list->Append(GetNetwork( (*it)->service_path(), - chromeos::NetworkMenu::IconForNetwork(*it), + *icon, (*it)->name(), (*it)->connecting(), (*it)->connected(), @@ -1088,9 +1091,10 @@ ListValue* InternetOptionsHandler::GetWirelessList() { cros_->cellular_networks(); for (chromeos::CellularNetworkVector::const_iterator it = cellular_networks.begin(); it != cellular_networks.end(); ++it) { + const SkBitmap* icon = chromeos::NetworkMenuIcon::GetBitmap(*it); list->Append(GetNetwork( (*it)->service_path(), - chromeos::NetworkMenu::IconForNetwork(*it), + *icon, (*it)->name(), (*it)->connecting(), (*it)->connected(), @@ -1129,9 +1133,10 @@ ListValue* InternetOptionsHandler::GetVPNList() { cros_->virtual_networks(); for (chromeos::VirtualNetworkVector::const_iterator it = virtual_networks.begin(); it != virtual_networks.end(); ++it) { + const SkBitmap* icon = chromeos::NetworkMenuIcon::GetBitmap(*it); list->Append(GetNetwork( (*it)->service_path(), - chromeos::NetworkMenu::IconForNetwork(*it), + *icon, (*it)->name(), (*it)->connecting(), (*it)->connected(), @@ -1159,9 +1164,11 @@ ListValue* InternetOptionsHandler::GetRememberedList() { // Set in_active_profile. bool shared = remembered->profile_type() == chromeos::PROFILE_SHARED; + const SkBitmap* icon = + chromeos::NetworkMenuIcon::GetBitmap(wifi ? wifi : remembered); list->Append(GetNetwork( remembered->service_path(), - chromeos::NetworkMenu::IconForNetwork(wifi ? wifi : remembered), + *icon, remembered->name(), wifi ? wifi->connecting() : false, wifi ? wifi->connected() : false, @@ -1183,9 +1190,11 @@ ListValue* InternetOptionsHandler::GetRememberedList() { // Set in_active_profile. bool shared = remembered->profile_type() == chromeos::PROFILE_SHARED; + const SkBitmap* icon = + chromeos::NetworkMenuIcon::GetBitmap(vpn ? vpn : remembered); list->Append(GetNetwork( remembered->service_path(), - chromeos::NetworkMenu::IconForNetwork(vpn ? vpn : remembered), + *icon, remembered->name(), vpn ? vpn->connecting() : false, vpn ? vpn->connected() : false, diff --git a/chrome/chrome_browser.gypi b/chrome/chrome_browser.gypi index 61ea952..8b9360ff 100644 --- a/chrome/chrome_browser.gypi +++ b/chrome/chrome_browser.gypi @@ -705,6 +705,8 @@ 'browser/chromeos/status/network_menu.h', 'browser/chromeos/status/network_menu_button.cc', 'browser/chromeos/status/network_menu_button.h', + 'browser/chromeos/status/network_menu_icon.cc', + 'browser/chromeos/status/network_menu_icon.h', 'browser/chromeos/status/power_menu_button.cc', 'browser/chromeos/status/power_menu_button.h', 'browser/chromeos/status/status_area_button.cc', |