1 // Copyright 2013 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.
5 #include "chrome/browser/apps/app_shim/app_shim_handler_mac.h"
10 #include "base/logging.h"
11 #include "base/memory/singleton.h"
12 #include "base/message_loop/message_loop.h"
13 #include "chrome/browser/apps/app_window_registry_util.h"
14 #include "chrome/browser/chrome_notification_types.h"
15 #include "chrome/browser/lifetime/application_lifetime.h"
16 #include "chrome/browser/ui/app_list/app_list_service.h"
17 #include "content/public/browser/notification_observer.h"
18 #include "content/public/browser/notification_registrar.h"
19 #include "content/public/browser/notification_service.h"
25 void TerminateIfNoAppWindows() {
26 bool app_windows_left
=
27 AppWindowRegistryUtil::IsAppWindowVisibleInAnyProfile(0);
28 if (!app_windows_left
&&
29 !AppListService::Get(chrome::HOST_DESKTOP_TYPE_NATIVE
)
30 ->IsAppListVisible()) {
31 chrome::AttemptExit();
35 class AppShimHandlerRegistry
: public content::NotificationObserver
{
37 static AppShimHandlerRegistry
* GetInstance() {
38 return base::Singleton
<
39 AppShimHandlerRegistry
,
40 base::LeakySingletonTraits
<AppShimHandlerRegistry
>>::get();
43 AppShimHandler
* GetForAppMode(const std::string
& app_mode_id
) const {
44 HandlerMap::const_iterator it
= handlers_
.find(app_mode_id
);
45 if (it
!= handlers_
.end())
48 return default_handler_
;
51 bool SetForAppMode(const std::string
& app_mode_id
, AppShimHandler
* handler
) {
52 bool inserted_or_removed
= handler
?
53 handlers_
.insert(HandlerMap::value_type(app_mode_id
, handler
)).second
:
54 handlers_
.erase(app_mode_id
) == 1;
55 DCHECK(inserted_or_removed
);
56 return inserted_or_removed
;
59 void SetDefaultHandler(AppShimHandler
* handler
) {
60 DCHECK_NE(default_handler_
== NULL
, handler
== NULL
);
61 default_handler_
= handler
;
64 void MaybeTerminate() {
65 if (!browser_session_running_
) {
66 // Post this to give AppWindows a chance to remove themselves from the
68 base::MessageLoop::current()->PostTask(
69 FROM_HERE
, base::Bind(&TerminateIfNoAppWindows
));
73 bool ShouldRestoreSession() {
74 return !browser_session_running_
;
78 friend struct base::DefaultSingletonTraits
<AppShimHandlerRegistry
>;
79 typedef std::map
<std::string
, AppShimHandler
*> HandlerMap
;
81 AppShimHandlerRegistry()
82 : default_handler_(NULL
),
83 browser_session_running_(false) {
85 this, chrome::NOTIFICATION_BROWSER_OPENED
,
86 content::NotificationService::AllBrowserContextsAndSources());
88 this, chrome::NOTIFICATION_CLOSE_ALL_BROWSERS_REQUEST
,
89 content::NotificationService::AllBrowserContextsAndSources());
91 this, chrome::NOTIFICATION_BROWSER_CLOSE_CANCELLED
,
92 content::NotificationService::AllBrowserContextsAndSources());
95 ~AppShimHandlerRegistry() override
{}
97 // content::NotificationObserver override:
98 void Observe(int type
,
99 const content::NotificationSource
& source
,
100 const content::NotificationDetails
& details
) override
{
102 case chrome::NOTIFICATION_BROWSER_OPENED
:
103 case chrome::NOTIFICATION_BROWSER_CLOSE_CANCELLED
:
104 browser_session_running_
= true;
106 case chrome::NOTIFICATION_CLOSE_ALL_BROWSERS_REQUEST
:
107 browser_session_running_
= false;
114 HandlerMap handlers_
;
115 AppShimHandler
* default_handler_
;
116 content::NotificationRegistrar registrar_
;
117 bool browser_session_running_
;
119 DISALLOW_COPY_AND_ASSIGN(AppShimHandlerRegistry
);
125 void AppShimHandler::RegisterHandler(const std::string
& app_mode_id
,
126 AppShimHandler
* handler
) {
128 AppShimHandlerRegistry::GetInstance()->SetForAppMode(app_mode_id
, handler
);
132 void AppShimHandler::RemoveHandler(const std::string
& app_mode_id
) {
133 AppShimHandlerRegistry::GetInstance()->SetForAppMode(app_mode_id
, NULL
);
137 AppShimHandler
* AppShimHandler::GetForAppMode(const std::string
& app_mode_id
) {
138 return AppShimHandlerRegistry::GetInstance()->GetForAppMode(app_mode_id
);
142 void AppShimHandler::SetDefaultHandler(AppShimHandler
* handler
) {
143 AppShimHandlerRegistry::GetInstance()->SetDefaultHandler(handler
);
147 void AppShimHandler::MaybeTerminate() {
148 AppShimHandlerRegistry::GetInstance()->MaybeTerminate();
152 bool AppShimHandler::ShouldRestoreSession() {
153 return AppShimHandlerRegistry::GetInstance()->ShouldRestoreSession();