blob: dbedc128651b0cc33c28a8fd150ceaeaf48fd5f0 [file] [log] [blame]
hironod36c21d2016-06-21 01:25:221// Copyright 2016 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
Evan Stadefdc58a82018-04-23 19:00:475#include "chrome/browser/notifications/arc_application_notifier_controller.h"
hironod36c21d2016-06-21 01:25:226
7#include <set>
8
Sebastien Marchandf1349f52019-01-25 03:16:419#include "base/bind.h"
hironod36c21d2016-06-21 01:25:2210#include "base/strings/utf_string_conversions.h"
11#include "chrome/browser/profiles/profile.h"
Evan Stadefdc58a82018-04-23 19:00:4712#include "chrome/browser/ui/app_list/arc/arc_app_list_prefs_factory.h"
13#include "components/keyed_service/content/browser_context_keyed_service_shutdown_notifier_factory.h"
hirono0bed5da2016-06-22 01:35:4514#include "ui/base/layout.h"
15#include "ui/display/display.h"
16#include "ui/display/screen.h"
Evan Stade889ce4712018-01-28 15:26:2617#include "ui/message_center/public/cpp/notifier_id.h"
hironod36c21d2016-06-21 01:25:2218
19namespace arc {
20
21namespace {
hirono0bed5da2016-06-22 01:35:4522constexpr int kArcAppIconSizeInDp = 48;
Evan Stadefdc58a82018-04-23 19:00:4723
24class ArcAppNotifierShutdownNotifierFactory
25 : public BrowserContextKeyedServiceShutdownNotifierFactory {
26 public:
27 static ArcAppNotifierShutdownNotifierFactory* GetInstance() {
28 return base::Singleton<ArcAppNotifierShutdownNotifierFactory>::get();
29 }
30
31 private:
32 friend struct base::DefaultSingletonTraits<
33 ArcAppNotifierShutdownNotifierFactory>;
34
35 ArcAppNotifierShutdownNotifierFactory()
36 : BrowserContextKeyedServiceShutdownNotifierFactory("ArcAppNotifier") {
37 DependsOn(ArcAppListPrefsFactory::GetInstance());
38 }
39
40 ~ArcAppNotifierShutdownNotifierFactory() override {}
41
42 DISALLOW_COPY_AND_ASSIGN(ArcAppNotifierShutdownNotifierFactory);
43};
44
hironod36c21d2016-06-21 01:25:2245} // namespace
46
Evan Stadefdc58a82018-04-23 19:00:4747ArcApplicationNotifierController::ArcApplicationNotifierController(
48 NotifierController::Observer* observer)
hironoe39df252016-06-24 03:17:1449 : observer_(observer), last_profile_(nullptr) {}
hironod36c21d2016-06-21 01:25:2250
Evan Stadefdc58a82018-04-23 19:00:4751ArcApplicationNotifierController::~ArcApplicationNotifierController() {
hironoe39df252016-06-24 03:17:1452 StopObserving();
53}
hirono0bed5da2016-06-22 01:35:4554
Evan Stade55575d82017-11-02 00:52:3655std::vector<ash::mojom::NotifierUiDataPtr>
Evan Stadefdc58a82018-04-23 19:00:4756ArcApplicationNotifierController::GetNotifierList(Profile* profile) {
Tetsui Ohkubod91be842018-07-03 01:35:2257 // In Guest mode, it can be called but there's no ARC apps to return.
58 if (profile->IsOffTheRecord())
59 return std::vector<ash::mojom::NotifierUiDataPtr>();
60
hironoe39df252016-06-24 03:17:1461 package_to_app_ids_.clear();
62 icons_.clear();
63 StopObserving();
64
65 ArcAppListPrefs* const app_list = ArcAppListPrefs::Get(profile);
Evan Stade55575d82017-11-02 00:52:3666 std::vector<ash::mojom::NotifierUiDataPtr> results;
Evan Stade51f736fc2017-10-25 05:26:1867 // The app list can be null in unit tests.
68 if (!app_list)
69 return results;
hironod36c21d2016-06-21 01:25:2270 const std::vector<std::string>& app_ids = app_list->GetAppIds();
hironod36c21d2016-06-21 01:25:2271
hironoe39df252016-06-24 03:17:1472 last_profile_ = profile;
Evan Stadefdc58a82018-04-23 19:00:4773 StartObserving();
hironoe39df252016-06-24 03:17:1474
hironod36c21d2016-06-21 01:25:2275 for (const std::string& app_id : app_ids) {
76 const auto app = app_list->GetApp(app_id);
hironod36c21d2016-06-21 01:25:2277 // Handle packages having multiple launcher activities.
hirono1f918652016-07-05 09:54:5478 if (!app || package_to_app_ids_.count(app->package_name))
79 continue;
80
81 const auto package = app_list->GetPackage(app->package_name);
82 if (!package || package->system)
hironod36c21d2016-06-21 01:25:2283 continue;
84
hirono0bed5da2016-06-22 01:35:4585 // Load icons for notifier.
Vladislav Kaznacheevcea52b092018-07-25 22:37:2786 std::unique_ptr<ArcAppIcon> icon =
87 std::make_unique<ArcAppIcon>(profile, app_id,
hirono0bed5da2016-06-22 01:35:4588 // ARC icon is available only for 48x48 dips.
89 kArcAppIconSizeInDp,
90 // The life time of icon must shorter than |this|.
Vladislav Kaznacheevcea52b092018-07-25 22:37:2791 this);
khmel832d8b72017-05-08 18:38:1192 // Apply icon now to set the default image.
93 OnIconUpdated(icon.get());
hirono0bed5da2016-06-22 01:35:4594
95 // Add notifiers.
hironoe39df252016-06-24 03:17:1496 package_to_app_ids_.insert(std::make_pair(app->package_name, app_id));
hironod36c21d2016-06-21 01:25:2297 message_center::NotifierId notifier_id(
Daniel Chenga925cbb52018-11-06 21:52:3598 message_center::NotifierType::ARC_APPLICATION, app_id);
Evan Stade55575d82017-11-02 00:52:3699 auto ui_data = ash::mojom::NotifierUiData::New(
Tetsui Ohkuboc27a5dc2018-01-11 05:56:52100 notifier_id, base::UTF8ToUTF16(app->name), app->notifications_enabled,
101 false /* enforced */, icon->image_skia());
hirono0bed5da2016-06-22 01:35:45102 icons_.push_back(std::move(icon));
Evan Stade51f736fc2017-10-25 05:26:18103 results.push_back(std::move(ui_data));
hironod36c21d2016-06-21 01:25:22104 }
105
106 return results;
107}
108
Evan Stadefdc58a82018-04-23 19:00:47109void ArcApplicationNotifierController::SetNotifierEnabled(
hironod36c21d2016-06-21 01:25:22110 Profile* profile,
Evan Stade844ad7f2017-09-20 18:05:31111 const message_center::NotifierId& notifier_id,
hironod36c21d2016-06-21 01:25:22112 bool enabled) {
Evan Stadefdc58a82018-04-23 19:00:47113 ArcAppListPrefs::Get(profile)->SetNotificationsEnabled(notifier_id.id,
114 enabled);
hironoe39df252016-06-24 03:17:14115 // OnNotifierEnabledChanged will be invoked via ArcAppListPrefs::Observer.
116}
117
Evan Stadefdc58a82018-04-23 19:00:47118void ArcApplicationNotifierController::OnIconUpdated(ArcAppIcon* icon) {
119 observer_->OnIconImageUpdated(
Daniel Chenga925cbb52018-11-06 21:52:35120 message_center::NotifierId(message_center::NotifierType::ARC_APPLICATION,
Evan Stadefdc58a82018-04-23 19:00:47121 icon->app_id()),
122 icon->image_skia());
123}
124
125void ArcApplicationNotifierController::OnNotificationsEnabledChanged(
hironoe39df252016-06-24 03:17:14126 const std::string& package_name,
127 bool enabled) {
128 auto it = package_to_app_ids_.find(package_name);
129 if (it == package_to_app_ids_.end())
130 return;
131 observer_->OnNotifierEnabledChanged(
Daniel Chenga925cbb52018-11-06 21:52:35132 message_center::NotifierId(message_center::NotifierType::ARC_APPLICATION,
hironoe39df252016-06-24 03:17:14133 it->second),
134 enabled);
hironod36c21d2016-06-21 01:25:22135}
136
Evan Stadefdc58a82018-04-23 19:00:47137void ArcApplicationNotifierController::StartObserving() {
138 ArcAppListPrefs::Get(last_profile_)->AddObserver(this);
139 shutdown_notifier_ = ArcAppNotifierShutdownNotifierFactory::GetInstance()
140 ->Get(last_profile_)
141 ->Subscribe(base::BindRepeating(
142 &ArcApplicationNotifierController::StopObserving,
143 base::Unretained(this)));
hirono0bed5da2016-06-22 01:35:45144}
145
Evan Stadefdc58a82018-04-23 19:00:47146void ArcApplicationNotifierController::StopObserving() {
hironoe39df252016-06-24 03:17:14147 if (!last_profile_)
148 return;
Evan Stadefdc58a82018-04-23 19:00:47149 shutdown_notifier_.reset();
150 ArcAppListPrefs::Get(last_profile_)->RemoveObserver(this);
hironoe39df252016-06-24 03:17:14151 last_profile_ = nullptr;
152}
153
hironod36c21d2016-06-21 01:25:22154} // namespace arc