Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(169)

Side by Side Diff: chrome/browser/chromeos/screensaver/screensaver_controller.cc

Issue 12093058: Screensaver implementation for ChromeOS. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: tests. Created 7 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
Matt Perry 2013/01/31 00:37:23 We have other systems that only support 1 active e
rkc 2013/01/31 02:15:46 So I spoke with Josh (the PM for this feature) and
Matt Perry 2013/01/31 22:43:51 OK, that seems fair.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "chrome/browser/chromeos/screensaver/screensaver_controller.h"
6
7 #include "ash/screensaver/screensaver_view.h"
8 #include "ash/shell.h"
9 #include "ash/wm/user_activity_detector.h"
10 #include "base/bind.h"
11 #include "base/callback.h"
12 #include "base/logging.h"
13 #include "chrome/browser/extensions/extension_service.h"
14 #include "chrome/browser/extensions/extension_system.h"
15 #include "chrome/browser/profiles/profile_manager.h"
16 #include "chrome/common/chrome_notification_types.h"
17 #include "chrome/common/extensions/extension.h"
18 #include "chromeos/dbus/dbus_thread_manager.h"
19 #include "chromeos/dbus/power_manager_client.h"
20 #include "content/public/browser/notification_service.h"
21
22 namespace {
23
24 const int kScreensaverTimeoutMs = 120000;
Matt Perry 2013/01/31 00:37:23 nit: could specify this in minutes, and use TimeDe
rkc 2013/01/31 02:15:46 Done.
25
26 ExtensionService* GetDefaultExtensionService() {
27 Profile* default_profile = ProfileManager::GetDefaultProfile();
Matt Perry 2013/01/31 00:37:23 This is generally a bad thing to do... But maybe i
rkc 2013/01/31 02:15:46 The default profile on ChromeOS will always be you
28 DCHECK(default_profile);
29 ExtensionService* service =
30 extensions::ExtensionSystem::Get(default_profile)->extension_service();
31 DCHECK(service);
32
33 return service;
34 }
35
36 // Find the screensaver extension for the given service, excluding
37 // the one with exclude_id.
38 std::string FindScreensaverExtension(ExtensionService* service,
39 const std::string& exclude_id) {
40 const ExtensionSet* extensions = service->extensions();
41 if (!extensions)
42 return std::string();
43
44 for (ExtensionSet::const_iterator it = extensions->begin();
45 it != extensions->end();
46 ++it) {
47 const extensions::Extension* extension = *it;
48 if (extension &&
49 extension->id() != exclude_id &&
50 extension->HasAPIPermission(extensions::APIPermission::kScreensaver))
51 return extension->id();
52 }
53
54 return std::string();
55 }
56
57 void UninstallPreviousScreensavers(const extensions::Extension* current) {
58 Profile* default_profile = ProfileManager::GetDefaultProfile();
59 DCHECK(default_profile);
60 ExtensionService* service =
61 extensions::ExtensionSystem::Get(default_profile)->extension_service();
62 DCHECK(service);
63
64 std::string screensaver_id;
65 while (!(screensaver_id = FindScreensaverExtension(service,
66 current->id())).empty()) {
Matt Perry 2013/01/31 00:37:23 indent
rkc 2013/01/31 02:15:46 Done.
Matt Perry 2013/01/31 22:43:51 (FYI I just meant that curret_id should be 1 space
67 string16 error;
68 if (!service->UninstallExtension(screensaver_id, false, &error))
69 LOG(ERROR) <<
70 "Couldn't uninstall previous screensaver extension with id: " <<
71 screensaver_id << " \nError: " << error;
72 }
73 }
74
75 } // namespace
76
77 namespace chromeos {
78
79 ScreensaverController::ScreensaverController()
80 : threshold_(base::TimeDelta::FromMilliseconds(kScreensaverTimeoutMs)),
81 weak_ptr_factory_(ALLOW_THIS_IN_INITIALIZER_LIST(this)) {
82 // Register for extension changes.
83 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_LOADED,
84 content::NotificationService::AllSources());
85 registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_UNLOADED,
86 content::NotificationService::AllSources());
87
88 std::string screensaver_extension_id =
89 FindScreensaverExtension(GetDefaultExtensionService(), std::string());
90 if (!screensaver_extension_id.empty())
91 SetupScreensaver(screensaver_extension_id);
92 }
93
94 ScreensaverController::~ScreensaverController() {
95 TeardownScreensaver();
96 }
97
98 void ScreensaverController::Observe(
99 int type,
100 const content::NotificationSource& source,
101 const content::NotificationDetails& details) {
102 switch (type) {
103 case chrome::NOTIFICATION_EXTENSION_INSTALLED: {
104 const extensions::Extension* extension =
105 content::Details<const extensions::Extension>(details).ptr();
106
107 // Uninstall any previously installed screensaver extensions.
108 UninstallPreviousScreensavers(extension);
Matt Perry 2013/01/31 00:37:23 I think you mean to do this only if |extension| is
rkc 2013/01/31 02:15:46 Whoops, yes, this will just unload any previous sc
109 break;
110 }
111 case chrome::NOTIFICATION_EXTENSION_LOADED: {
112 const extensions::Extension* extension =
113 content::Details<const extensions::Extension>(details).ptr();
114 if (!extension->HasAPIPermission(extensions::APIPermission::kScreensaver))
115 return;
Matt Perry 2013/01/31 00:37:23 indent
rkc 2013/01/31 02:15:46 Done.
116
117 SetupScreensaver(extension->id());
118 break;
119 }
120 case chrome::NOTIFICATION_EXTENSION_UNLOADED: {
121 const extensions::Extension* extension =
122 content::Details<extensions::UnloadedExtensionInfo>(
123 details)->extension;
124 if (extension->HasAPIPermission(extensions::APIPermission::kScreensaver))
Matt Perry 2013/01/31 00:37:23 might be clearer to just test if the id matches sc
rkc 2013/01/31 02:15:46 Done.
125 TeardownScreensaver();
126 break;
127 }
128 }
129 }
130
131 void ScreensaverController::IdleNotify(int64 threshold) {
132 ExtensionService* service = GetDefaultExtensionService();
133 const extensions::Extension* screensaver_extension =
134 service->GetExtensionById(screensaver_extension_id_,
135 ExtensionService::INCLUDE_ENABLED);
136 ash::ShowScreensaver(screensaver_extension->GetFullLaunchURL());
Matt Perry 2013/01/31 00:37:23 interesting.. so a screensaver is just an app with
rkc 2013/01/31 02:15:46 Yep, that's how the screensaver is implemented in
137
138 ash::Shell::GetInstance()->user_activity_detector()->AddObserver(this);
139 }
140
141 void ScreensaverController::OnUserActivity() {
142 // We don't want to handle further user notifications; we'll either login
143 // the user and close out or or at least close the screensaver.
144 ash::Shell::GetInstance()->user_activity_detector()->RemoveObserver(this);
145 ash::CloseScreensaver();
146
147 RequestNextIdleNotification();
148 }
149
150 void ScreensaverController::SetupScreensaver(
151 const std::string& screensaver_extension_id) {
152 screensaver_extension_id_ = screensaver_extension_id;
153
154 PowerManagerClient* power_manager =
155 DBusThreadManager::Get()->GetPowerManagerClient();
156 if (!power_manager->HasObserver(this))
157 power_manager->AddObserver(this);
158
159 RequestNextIdleNotification();
160 }
161
162 void ScreensaverController::TeardownScreensaver() {
163 PowerManagerClient* power_manager =
164 DBusThreadManager::Get()->GetPowerManagerClient();
165 if (power_manager && power_manager->HasObserver(this))
166 power_manager->RemoveObserver(this);
167
168 if (ash::Shell::GetInstance() &&
169 ash::Shell::GetInstance()->user_activity_detector()->HasObserver(this))
170 ash::Shell::GetInstance()->user_activity_detector()->RemoveObserver(this);
171
172 ash::CloseScreensaver();
173 screensaver_extension_id_ = "";
174 }
175
176 void ScreensaverController::RequestNextIdleNotification() {
177 DBusThreadManager::Get()->GetPowerManagerClient()->
178 RequestIdleNotification(kScreensaverTimeoutMs);
179 }
180
181 } // namespace chromeos
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698