0

Add Ash notification UI for OutOfCredits network property

BUG=177240
for ash.gyp, ash/ash_chromeos_strings.grdp
TBR=sky@chromium.org

Review URL: https://codereview.chromium.org/12779022

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@189051 0039d316-1c4b-4281-b951-d872f2087c98
This commit is contained in:
stevenjb@chromium.org
2013-03-19 17:28:19 +00:00
parent 8b10406075
commit 1e88f380bb
15 changed files with 242 additions and 83 deletions

@ -201,6 +201,7 @@
'system/chromeos/network/network_state_list_detailed_view.h',
'system/chromeos/network/network_state_notifier.cc',
'system/chromeos/network/network_state_notifier.h',
'system/chromeos/network/network_tray_delegate.h',
'system/chromeos/network/tray_network.cc',
'system/chromeos/network/tray_network.h',
'system/chromeos/network/tray_network_state_observer.cc',

@ -117,6 +117,15 @@
<message name="IDS_NETWORK_CONNECTION_ERROR_MESSAGE_WITH_DETAILS" desc="Message for network connection error notification with details">
Failed to connect to network '<ph name="name">$1<ex>GoogleGuest</ex></ph>': <ph name="details">$2<ex>Unrecognized error</ex></ph>
</message>
<message name="IDS_NETWORK_OUT_OF_CREDITS_TITLE" desc="Title for network out of data error notification">
Network Connection Error
</message>
<message name="IDS_NETWORK_OUT_OF_CREDITS_BODY" desc="Message body for network out of data error notification">
You may have used up your mobile data allowance.
</message>
<message name="IDS_NETWORK_OUT_OF_CREDITS_LINK" desc="Link text for network out of data error notification">
Visit the <ph name="name">$1<ex>GoogleGuest</ex></ph> activation portal to buy more data.
</message>
<!-- Network state strings -->
<message name="IDS_CHROMEOS_NETWORK_STATE_UNKNOWN" desc="Network state in about:network: UNKNOWN">

@ -12,20 +12,14 @@
namespace ash {
struct NetworkIconInfo;
class NetworkTrayDelegate {
public:
virtual ~NetworkTrayDelegate() {}
// Notifies that the |index|-th link on the notification is clicked.
virtual void NotificationLinkClicked(size_t index) = 0;
};
class NetworkTrayDelegate;
class NetworkObserver {
public:
enum MessageType {
// Priority order, highest to lowest.
ERROR_CONNECT_FAILED,
ERROR_OUT_OF_CREDITS,
MESSAGE_DATA_PROMO,
};

@ -4,9 +4,11 @@
#include "ash/system/chromeos/network/network_state_notifier.h"
#include "ash/ash_switches.h"
#include "ash/shell.h"
#include "ash/system/chromeos/network/network_observer.h"
#include "ash/system/tray/system_tray_notifier.h"
#include "base/command_line.h"
#include "base/string16.h"
#include "base/utf_string_conversions.h"
#include "chromeos/network/network_event_log.h"
@ -16,12 +18,25 @@
#include "third_party/cros_system_api/dbus/service_constants.h"
#include "ui/base/l10n/l10n_util.h"
using chromeos::NetworkState;
using chromeos::NetworkStateHandler;
namespace {
const char kLogModule[] = "NetworkStateNotifier";
ash::NetworkObserver::NetworkType GetAshNetworkType(const std::string& type) {
if (type == flimflam::kTypeCellular)
return ash::NetworkObserver::NETWORK_CELLULAR;
const int kMinTimeBetweenOutOfCreditsNotifySeconds = 10 * 60;
ash::NetworkObserver::NetworkType GetAshNetworkType(
const NetworkState* network) {
const std::string& type = network->type();
if (type == flimflam::kTypeCellular) {
if (network->technology() == flimflam::kNetworkTechnologyLte ||
network->technology() == flimflam::kNetworkTechnologyLteAdvanced)
return ash::NetworkObserver::NETWORK_CELLULAR_LTE;
else
return ash::NetworkObserver::NETWORK_CELLULAR;
}
if (type == flimflam::kTypeEthernet)
return ash::NetworkObserver::NETWORK_ETHERNET;
if (type == flimflam::kTypeWifi)
@ -87,17 +102,15 @@ string16 GetErrorString(const std::string& error) {
} // namespace
using chromeos::NetworkState;
using chromeos::NetworkStateHandler;
namespace ash {
namespace internal {
NetworkStateNotifier::NetworkStateNotifier() {
if (NetworkStateHandler::Get()) {
NetworkStateHandler::Get()->AddObserver(this);
InitializeNetworks();
}
NetworkStateNotifier::NetworkStateNotifier()
: cellular_out_of_credits_(false) {
if (!NetworkStateHandler::Get())
return;
NetworkStateHandler::Get()->AddObserver(this);
InitializeNetworks();
}
NetworkStateNotifier::~NetworkStateNotifier() {
@ -105,6 +118,11 @@ NetworkStateNotifier::~NetworkStateNotifier() {
NetworkStateHandler::Get()->RemoveObserver(this);
}
void NetworkStateNotifier::DefaultNetworkChanged(const NetworkState* network) {
if (network)
last_default_network_ = network->path();
}
void NetworkStateNotifier::NetworkConnectionStateChanged(
const NetworkState* network) {
NetworkStateHandler* handler = NetworkStateHandler::Get();
@ -143,11 +161,10 @@ void NetworkStateNotifier::NetworkConnectionStateChanged(
kLogModule, "ConnectionFailure", network->path());
std::vector<string16> no_links;
ash::NetworkObserver::NetworkType network_type =
GetAshNetworkType(network->type());
ash::NetworkObserver::NetworkType network_type = GetAshNetworkType(network);
string16 error = GetErrorString(network->error());
ash::Shell::GetInstance()->system_tray_notifier()->NotifySetNetworkMessage(
NULL, ash::NetworkObserver::ERROR_CONNECT_FAILED, network_type,
this, ash::NetworkObserver::ERROR_CONNECT_FAILED, network_type,
l10n_util::GetStringUTF16(IDS_NETWORK_CONNECTION_ERROR_TITLE),
l10n_util::GetStringFUTF16(
IDS_NETWORK_CONNECTION_ERROR_MESSAGE_WITH_DETAILS,
@ -155,6 +172,58 @@ void NetworkStateNotifier::NetworkConnectionStateChanged(
no_links);
}
void NetworkStateNotifier::NetworkPropertiesUpdated(
const NetworkState* network) {
DCHECK(network);
if (CommandLine::ForCurrentProcess()->HasSwitch(
ash::switches::kAshDisableNewNetworkStatusArea)) {
return;
}
// Trigger "Out of credits" notification if the cellular network is the most
// recent default network (i.e. we have not switched to another network).
if (network->type() == flimflam::kTypeCellular &&
network->path() == last_default_network_) {
cellular_network_ = network->path();
if (network->cellular_out_of_credits() &&
!cellular_out_of_credits_) {
cellular_out_of_credits_ = true;
base::TimeDelta dtime = base::Time::Now() - out_of_credits_notify_time_;
if (dtime.InSeconds() > kMinTimeBetweenOutOfCreditsNotifySeconds) {
out_of_credits_notify_time_ = base::Time::Now();
ash::NetworkObserver::NetworkType network_type =
GetAshNetworkType(network);
std::vector<string16> links;
links.push_back(
l10n_util::GetStringFUTF16(IDS_NETWORK_OUT_OF_CREDITS_LINK,
UTF8ToUTF16(network->name())));
ash::Shell::GetInstance()->system_tray_notifier()->
NotifySetNetworkMessage(
this, ash::NetworkObserver::ERROR_OUT_OF_CREDITS, network_type,
l10n_util::GetStringUTF16(IDS_NETWORK_OUT_OF_CREDITS_TITLE),
l10n_util::GetStringUTF16(IDS_NETWORK_OUT_OF_CREDITS_BODY),
links);
}
} else if (!network->cellular_out_of_credits() &&
cellular_out_of_credits_) {
cellular_out_of_credits_ = false;
}
}
}
void NetworkStateNotifier::NotificationLinkClicked(
NetworkObserver::MessageType message_type,
size_t link_index) {
if (message_type == ash::NetworkObserver::ERROR_OUT_OF_CREDITS) {
if (!cellular_network_.empty()) {
// This will trigger the activation / portal code.
Shell::GetInstance()->system_tray_delegate()->ConnectToNetwork(
cellular_network_);
}
ash::Shell::GetInstance()->system_tray_notifier()->
NotifyClearNetworkMessage(message_type);
}
}
void NetworkStateNotifier::InitializeNetworks() {
NetworkStateList network_list;
NetworkStateHandler::Get()->GetNetworkList(&network_list);
@ -166,6 +235,10 @@ void NetworkStateNotifier::InitializeNetworks() {
VLOG(2) << " Network: " << network->path();
cached_state_[network->path()] = network->connection_state();
}
const NetworkState* default_network =
NetworkStateHandler::Get()->DefaultNetwork();
if (default_network)
last_default_network_ = default_network->path();
}
} // namespace internal

@ -8,8 +8,10 @@
#include <map>
#include "ash/ash_export.h"
#include "ash/system/chromeos/network/network_tray_delegate.h"
#include "base/basictypes.h"
#include "base/compiler_specific.h"
#include "base/time.h"
#include "chromeos/network/network_state_handler_observer.h"
namespace ash {
@ -18,14 +20,24 @@ namespace internal {
// This class observes NetworkStateHandler and generates notifications
// on connection failures.
class ASH_EXPORT NetworkStateNotifier :
public chromeos::NetworkStateHandlerObserver {
public chromeos::NetworkStateHandlerObserver,
public NetworkTrayDelegate {
public:
NetworkStateNotifier();
virtual ~NetworkStateNotifier();
// NetworkStateHandlerObserver
virtual void DefaultNetworkChanged(
const chromeos::NetworkState* network) OVERRIDE;
virtual void NetworkConnectionStateChanged(
const chromeos::NetworkState* network) OVERRIDE;
virtual void NetworkPropertiesUpdated(
const chromeos::NetworkState* network) OVERRIDE;
// NetworkTrayDelegate
virtual void NotificationLinkClicked(
NetworkObserver::MessageType message_type,
size_t link_index) OVERRIDE;
private:
typedef std::map<std::string, std::string> CachedStateMap;
@ -33,6 +45,10 @@ class ASH_EXPORT NetworkStateNotifier :
void InitializeNetworks();
CachedStateMap cached_state_;
std::string last_default_network_;
std::string cellular_network_;
bool cellular_out_of_credits_;
base::Time out_of_credits_notify_time_;
DISALLOW_COPY_AND_ASSIGN(NetworkStateNotifier);
};

@ -0,0 +1,24 @@
// Copyright (c) 2012 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 ASH_SYSTEM_CHROMEOS_NETWORK_NETWORK_TRAY_DELEGATE_H
#define ASH_SYSTEM_CHROMEOS_NETWORK_NETWORK_TRAY_DELEGATE_H
#include "ash/system/chromeos/network/network_observer.h"
namespace ash {
class NetworkTrayDelegate {
public:
virtual ~NetworkTrayDelegate() {}
// Notifies that the |index|-th link on the notification is clicked.
virtual void NotificationLinkClicked(
NetworkObserver::MessageType message_type,
size_t link_index) = 0;
};
} // namespace ash
#endif // ASH_SYSTEM_CHROMEOS_NETWORK_NETWORK_TRAY_DELEGATE_H

@ -11,6 +11,7 @@
#include "ash/system/chromeos/network/network_list_detailed_view_base.h"
#include "ash/system/chromeos/network/network_state_list_detailed_view.h"
#include "ash/system/chromeos/network/network_state_notifier.h"
#include "ash/system/chromeos/network/network_tray_delegate.h"
#include "ash/system/tray/system_tray.h"
#include "ash/system/tray/system_tray_delegate.h"
#include "ash/system/tray/system_tray_notifier.h"
@ -33,23 +34,23 @@
#include "ui/views/layout/box_layout.h"
#include "ui/views/widget/widget.h"
using ash::internal::TrayNetwork;
using ash::NetworkObserver;
using chromeos::NetworkState;
using chromeos::NetworkStateHandler;
namespace {
using ash::internal::TrayNetwork;
int GetMessageIcon(
TrayNetwork::MessageType message_type,
TrayNetwork::NetworkType network_type) {
int GetMessageIcon(NetworkObserver::MessageType message_type,
NetworkObserver::NetworkType network_type) {
switch(message_type) {
case TrayNetwork::ERROR_CONNECT_FAILED:
if (TrayNetwork::NETWORK_CELLULAR == network_type)
case NetworkObserver::ERROR_CONNECT_FAILED:
if (NetworkObserver::NETWORK_CELLULAR == network_type)
return IDR_AURA_UBER_TRAY_CELLULAR_NETWORK_FAILED;
else
return IDR_AURA_UBER_TRAY_NETWORK_FAILED;
case TrayNetwork::MESSAGE_DATA_PROMO:
case NetworkObserver::ERROR_OUT_OF_CREDITS:
case NetworkObserver::MESSAGE_DATA_PROMO:
if (network_type == TrayNetwork::NETWORK_CELLULAR_LTE)
return IDR_AURA_UBER_TRAY_NOTIFICATION_LTE;
else
@ -77,7 +78,7 @@ class NetworkMessages {
struct Message {
Message() : delegate(NULL) {}
Message(NetworkTrayDelegate* in_delegate,
TrayNetwork::NetworkType network_type,
NetworkObserver::NetworkType network_type,
const string16& in_title,
const string16& in_message,
const std::vector<string16>& in_links) :
@ -87,12 +88,12 @@ class NetworkMessages {
message(in_message),
links(in_links) {}
NetworkTrayDelegate* delegate;
TrayNetwork::NetworkType network_type_;
NetworkObserver::NetworkType network_type_;
string16 title;
string16 message;
std::vector<string16> links;
};
typedef std::map<TrayNetwork::MessageType, Message> MessageMap;
typedef std::map<NetworkObserver::MessageType, Message> MessageMap;
MessageMap& messages() { return messages_; }
const MessageMap& messages() const { return messages_; }
@ -295,7 +296,7 @@ class NetworkMessageView : public views::View,
public views::LinkListener {
public:
NetworkMessageView(TrayNetwork* tray_network,
TrayNetwork::MessageType message_type,
NetworkObserver::MessageType message_type,
const NetworkMessages::Message& network_msg)
: tray_network_(tray_network),
message_type_(message_type),
@ -339,13 +340,13 @@ class NetworkMessageView : public views::View,
tray_network_->LinkClicked(message_type_, source->id());
}
TrayNetwork::MessageType message_type() const { return message_type_; }
TrayNetwork::NetworkType network_type() const { return network_type_; }
NetworkObserver::MessageType message_type() const { return message_type_; }
NetworkObserver::NetworkType network_type() const { return network_type_; }
private:
TrayNetwork* tray_network_;
TrayNetwork::MessageType message_type_;
TrayNetwork::NetworkType network_type_;
NetworkObserver::MessageType message_type_;
NetworkObserver::NetworkType network_type_;
DISALLOW_COPY_AND_ASSIGN(NetworkMessageView);
};
@ -498,11 +499,11 @@ void TrayNetwork::OnNetworkRefresh(const NetworkIconInfo& info) {
}
void TrayNetwork::SetNetworkMessage(NetworkTrayDelegate* delegate,
MessageType message_type,
NetworkType network_type,
const string16& title,
const string16& message,
const std::vector<string16>& links) {
MessageType message_type,
NetworkType network_type,
const string16& title,
const string16& message,
const std::vector<string16>& links) {
messages_->messages()[message_type] = tray::NetworkMessages::Message(
delegate, network_type, title, message, links);
if (notification_)
@ -619,7 +620,7 @@ void TrayNetwork::LinkClicked(MessageType message_type, int link_id) {
tray::NetworkMessages::MessageMap::const_iterator iter =
messages()->messages().find(message_type);
if (iter != messages()->messages().end() && iter->second.delegate)
iter->second.delegate->NotificationLinkClicked(link_id);
iter->second.delegate->NotificationLinkClicked(message_type, link_id);
}
} // namespace internal

@ -109,6 +109,7 @@ EnumMapper<PropertyIndex>::Pair property_index_table[] = {
{ flimflam::kOfflineModeProperty, PROPERTY_INDEX_OFFLINE_MODE },
{ flimflam::kOperatorCodeProperty, PROPERTY_INDEX_OPERATOR_CODE },
{ flimflam::kOperatorNameProperty, PROPERTY_INDEX_OPERATOR_NAME },
{ shill::kOutOfCreditsProperty, PROPERTY_INDEX_OUT_OF_CREDITS },
{ flimflam::kPRLVersionProperty, PROPERTY_INDEX_PRL_VERSION },
{ flimflam::kPassphraseProperty, PROPERTY_INDEX_PASSPHRASE },
{ flimflam::kPassphraseRequiredProperty, PROPERTY_INDEX_PASSPHRASE_REQUIRED },
@ -962,6 +963,14 @@ bool NativeCellularNetworkParser::ParseValue(PropertyIndex index,
cellular_network->set_operator_code(value_str);
return true;
}
case PROPERTY_INDEX_OUT_OF_CREDITS: {
bool out_of_credits;
if (value.GetAsBoolean(&out_of_credits)) {
cellular_network->set_out_of_credits(out_of_credits);
return true;
}
break;
}
case PROPERTY_INDEX_SERVING_OPERATOR: {
if (value.IsType(base::Value::TYPE_DICTIONARY)) {
const DictionaryValue& dict =

@ -149,6 +149,7 @@ enum PropertyIndex {
PROPERTY_INDEX_OPEN_VPN_USER,
PROPERTY_INDEX_OPERATOR_CODE,
PROPERTY_INDEX_OPERATOR_NAME,
PROPERTY_INDEX_OUT_OF_CREDITS,
PROPERTY_INDEX_PASSPHRASE,
PROPERTY_INDEX_PASSPHRASE_REQUIRED,
PROPERTY_INDEX_PORTAL_URL,

@ -859,6 +859,7 @@ void CellularApn::Set(const DictionaryValue& dict) {
CellularNetwork::CellularNetwork(const std::string& service_path)
: WirelessNetwork(service_path, TYPE_CELLULAR),
activate_over_non_cellular_network_(false),
out_of_credits_(false),
activation_state_(ACTIVATION_STATE_UNKNOWN),
network_technology_(NETWORK_TECHNOLOGY_UNKNOWN),
roaming_state_(ROAMING_STATE_UNKNOWN),

@ -888,6 +888,7 @@ class CellularNetwork : public WirelessNetwork {
const std::string& operator_name() const { return operator_name_; }
const std::string& operator_code() const { return operator_code_; }
const std::string& operator_country() const { return operator_country_; }
bool out_of_credits() const { return out_of_credits_; }
const std::string& payment_url() const { return payment_url_; }
const std::string& usage_url() const { return usage_url_; }
const std::string& post_data() const { return post_data_; }
@ -955,6 +956,9 @@ class CellularNetwork : public WirelessNetwork {
void set_operator_country(const std::string& operator_country) {
operator_country_ = operator_country;
}
void set_out_of_credits(bool out_of_credits) {
out_of_credits_ = out_of_credits;
}
void set_payment_url(const std::string& payment_url) {
payment_url_ = payment_url;
}
@ -971,6 +975,7 @@ class CellularNetwork : public WirelessNetwork {
}
bool activate_over_non_cellular_network_;
bool out_of_credits_;
ActivationState activation_state_;
NetworkTechnology network_technology_;
NetworkRoamingState roaming_state_;

@ -981,7 +981,8 @@ void NetworkMenu::DoConnect(Network* network) {
}
} else if (network->type() == TYPE_CELLULAR) {
CellularNetwork* cellular = static_cast<CellularNetwork*>(network);
if (cellular->activation_state() != ACTIVATION_STATE_ACTIVATED) {
if (cellular->activation_state() != ACTIVATION_STATE_ACTIVATED ||
cellular->out_of_credits()) {
ActivateCellular(cellular);
} else {
cros->ConnectToCellularNetwork(cellular);
@ -1026,7 +1027,7 @@ void NetworkMenu::ConnectToNetwork(Network* network) {
case TYPE_CELLULAR: {
CellularNetwork* cell = static_cast<CellularNetwork*>(network);
if (cell->NeedsActivation()) {
if (cell->NeedsActivation() || cell->out_of_credits()) {
ActivateCellular(cell);
} else if (cell->connecting_or_connected() ||
cell->activation_state() == ACTIVATION_STATE_ACTIVATING) {

@ -17,6 +17,7 @@
#include "ash/system/bluetooth/bluetooth_observer.h"
#include "ash/system/brightness/brightness_observer.h"
#include "ash/system/chromeos/network/network_observer.h"
#include "ash/system/chromeos/network/network_tray_delegate.h"
#include "ash/system/date/clock_observer.h"
#include "ash/system/drive/drive_observer.h"
#include "ash/system/ime/ime_observer.h"
@ -189,6 +190,14 @@ void BluetoothDeviceConnectError(
// TODO(sad): Do something?
}
ash::NetworkObserver::NetworkType NetworkTypeForCellular(
const CellularNetwork* cellular) {
if (cellular->network_technology() == NETWORK_TECHNOLOGY_LTE ||
cellular->network_technology() == NETWORK_TECHNOLOGY_LTE_ADVANCED)
return ash::NetworkObserver::NETWORK_CELLULAR_LTE;
return ash::NetworkObserver::NETWORK_CELLULAR;
}
class SystemTrayDelegate : public ash::SystemTrayDelegate,
public AudioHandler::VolumeObserver,
public PowerManagerClient::Observer,
@ -222,6 +231,7 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
screen_locked_(false),
data_promo_notification_(new DataPromoNotification()),
cellular_activating_(false),
cellular_out_of_credits_(false),
volume_control_delegate_(new VolumeController()) {
// Register notifications on construction so that events such as
// PROFILE_CREATED do not get missed if they happen before Initialize().
@ -750,18 +760,10 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
virtual void ConnectToNetwork(const std::string& network_id) OVERRIDE {
NetworkLibrary* crosnet = CrosLibrary::Get()->GetNetworkLibrary();
Network* network = crosnet->FindNetworkByPath(network_id);
if (!CommandLine::ForCurrentProcess()->HasSwitch(
ash::switches::kAshDisableNewNetworkStatusArea)) {
// If the new network handlers are enabled, this should always trigger
// displaying the network settings UI.
if (network)
network_menu_->ShowTabbedNetworkSettings(network);
else
ShowNetworkSettings();
} else {
if (network)
network_menu_->ConnectToNetwork(network);
}
if (network)
network_menu_->ConnectToNetwork(network); // Shows settings if connected
else
ShowNetworkSettings();
}
virtual void RequestNetworkScan() OVERRIDE {
@ -1023,14 +1025,6 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
}
}
void RefreshNetworkDeviceObserver(NetworkLibrary* crosnet) {
const NetworkDevice* cellular = crosnet->FindCellularDevice();
std::string new_cellular_device_path = cellular ?
cellular->device_path() : std::string();
if (cellular_device_path_ != new_cellular_device_path)
cellular_device_path_ = new_cellular_device_path;
}
void AddNetworkToList(std::vector<ash::NetworkIconInfo>* list,
std::set<const Network*>* added,
const Network* network) {
@ -1150,10 +1144,9 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
// Overridden from NetworkLibrary::NetworkManagerObserver.
virtual void OnNetworkManagerChanged(NetworkLibrary* crosnet) OVERRIDE {
RefreshNetworkObserver(crosnet);
RefreshNetworkDeviceObserver(crosnet);
data_promo_notification_->ShowOptionalMobileDataPromoNotification(
crosnet, GetPrimarySystemTray(), this);
UpdateCellularActivation();
UpdateCellular();
NotifyRefreshNetwork();
}
@ -1358,7 +1351,19 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
}
// Overridden from ash::NetworkTrayDelegate
virtual void NotificationLinkClicked(size_t index) OVERRIDE {
virtual void NotificationLinkClicked(
ash::NetworkObserver::MessageType message_type,
size_t link_index) OVERRIDE {
if (message_type == ash::NetworkObserver::ERROR_OUT_OF_CREDITS) {
const CellularNetwork* cellular =
CrosLibrary::Get()->GetNetworkLibrary()->cellular_network();
if (cellular)
ConnectToNetwork(cellular->service_path());
ash::Shell::GetInstance()->system_tray_notifier()->
NotifyClearNetworkMessage(message_type);
}
if (message_type != ash::NetworkObserver::MESSAGE_DATA_PROMO)
return;
// If we have deal info URL defined that means that there're
// 2 links in bubble. Let the user close it manually then thus giving
// ability to navigate to second link.
@ -1369,7 +1374,7 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
data_promo_notification_->CloseNotification();
std::string deal_url_to_open;
if (index == 0) {
if (link_index == 0) {
if (!deal_topup_url.empty()) {
deal_url_to_open = deal_topup_url;
} else {
@ -1380,7 +1385,7 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
network_menu_->ShowTabbedNetworkSettings(cellular);
return;
}
} else if (index == 1) {
} else if (link_index == 1) {
deal_url_to_open = deal_info_url;
}
@ -1410,7 +1415,7 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
UpdateEnterpriseDomain();
}
void UpdateCellularActivation() {
void UpdateCellular() {
const CellularNetworkVector& cellular_networks =
CrosLibrary::Get()->GetNetworkLibrary()->cellular_networks();
if (cellular_networks.empty())
@ -1422,15 +1427,7 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
cellular_activating_ = true;
} else if (cellular->activated() && cellular_activating_) {
cellular_activating_ = false;
// Detect which icon to show, 3G or LTE.
ash::NetworkObserver::NetworkType type =
(cellular->network_technology() == NETWORK_TECHNOLOGY_LTE ||
cellular->network_technology() == NETWORK_TECHNOLOGY_LTE_ADVANCED)
? ash::NetworkObserver::NETWORK_CELLULAR_LTE
: ash::NetworkObserver::NETWORK_CELLULAR;
// Show the notification.
ash::NetworkObserver::NetworkType type = NetworkTypeForCellular(cellular);
ash::Shell::GetInstance()->system_tray_notifier()->
NotifySetNetworkMessage(
NULL,
@ -1443,6 +1440,27 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
UTF8ToUTF16((cellular->name()))),
std::vector<string16>());
}
if (!CommandLine::ForCurrentProcess()->HasSwitch(
ash::switches::kAshDisableNewNetworkStatusArea)) {
return;
}
// Trigger "Out of credits" notification (for NetworkLibrary impl)
if (cellular->out_of_credits() && !cellular_out_of_credits_) {
cellular_out_of_credits_ = true;
ash::NetworkObserver::NetworkType type = NetworkTypeForCellular(cellular);
std::vector<string16> links;
links.push_back(
l10n_util::GetStringFUTF16(IDS_NETWORK_OUT_OF_CREDITS_LINK,
UTF8ToUTF16(cellular->name())));
ash::Shell::GetInstance()->system_tray_notifier()->
NotifySetNetworkMessage(
this, ash::NetworkObserver::ERROR_OUT_OF_CREDITS, type,
l10n_util::GetStringUTF16(IDS_NETWORK_OUT_OF_CREDITS_TITLE),
l10n_util::GetStringUTF16(IDS_NETWORK_OUT_OF_CREDITS_BODY),
links);
} else if (!cellular->out_of_credits() && cellular_out_of_credits_) {
cellular_out_of_credits_ = false;
}
}
scoped_ptr<base::WeakPtrFactory<SystemTrayDelegate> > ui_weak_ptr_factory_;
@ -1453,7 +1471,6 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
content::NotificationRegistrar registrar_;
PrefChangeRegistrar local_state_registrar_;
scoped_ptr<PrefChangeRegistrar> user_pref_registrar_;
std::string cellular_device_path_;
std::string active_network_path_;
PowerSupplyStatus power_supply_status_;
base::HourClockType clock_type_;
@ -1467,6 +1484,7 @@ class SystemTrayDelegate : public ash::SystemTrayDelegate,
scoped_ptr<DataPromoNotification> data_promo_notification_;
bool cellular_activating_;
bool cellular_out_of_credits_;
scoped_ptr<ash::VolumeControlDelegate> volume_control_delegate_;

@ -42,6 +42,8 @@ bool NetworkState::PropertyChanged(const std::string& key,
return GetStringValue(key, value, &guid_);
} else if (key == shill::kActivateOverNonCellularNetworkProperty) {
return GetBooleanValue(key, value, &activate_over_non_cellular_networks_);
} else if (key == shill::kOutOfCreditsProperty) {
return GetBooleanValue(key, value, &cellular_out_of_credits_);
}
return false;
}
@ -71,6 +73,8 @@ void NetworkState::GetProperties(base::DictionaryValue* dictionary) const {
dictionary->SetBooleanWithoutPathExpansion(
shill::kActivateOverNonCellularNetworkProperty,
activate_over_non_cellular_networks());
dictionary->SetBooleanWithoutPathExpansion(shill::kOutOfCreditsProperty,
cellular_out_of_credits());
}
bool NetworkState::IsConnectedState() const {

@ -49,6 +49,7 @@ class CHROMEOS_EXPORT NetworkState : public ManagedState {
bool activate_over_non_cellular_networks() const {
return activate_over_non_cellular_networks_;
}
bool cellular_out_of_credits() const { return cellular_out_of_credits_; }
bool IsConnectedState() const;
bool IsConnectingState() const;
@ -80,6 +81,7 @@ class CHROMEOS_EXPORT NetworkState : public ManagedState {
std::string activation_state_;
std::string roaming_;
bool activate_over_non_cellular_networks_;
bool cellular_out_of_credits_;
DISALLOW_COPY_AND_ASSIGN(NetworkState);
};