- add sources.
[platform/framework/web/crosswalk.git] / src / chrome / browser / ui / ash / launcher / launcher_context_menu.cc
1 // Copyright (c) 2012 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
5 #include "chrome/browser/ui/ash/launcher/launcher_context_menu.h"
6
7 #include <string>
8
9 #include "ash/desktop_background/user_wallpaper_delegate.h"
10 #include "ash/root_window_controller.h"
11 #include "ash/shelf/shelf_widget.h"
12 #include "ash/shell.h"
13 #include "ash/shell_delegate.h"
14 #include "base/bind.h"
15 #include "base/command_line.h"
16 #include "base/prefs/pref_service.h"
17 #include "chrome/browser/extensions/context_menu_matcher.h"
18 #include "chrome/browser/extensions/extension_prefs.h"
19 #include "chrome/browser/fullscreen.h"
20 #include "chrome/browser/prefs/incognito_mode_prefs.h"
21 #include "chrome/browser/profiles/profile.h"
22 #include "chrome/browser/ui/ash/chrome_shell_delegate.h"
23 #include "chrome/browser/ui/ash/launcher/chrome_launcher_controller.h"
24 #include "chrome/common/chrome_switches.h"
25 #include "content/public/common/context_menu_params.h"
26 #include "grit/ash_strings.h"
27 #include "grit/generated_resources.h"
28 #include "ui/base/l10n/l10n_util.h"
29
30 namespace {
31
32 bool MenuItemHasLauncherContext(const extensions::MenuItem* item) {
33   return item->contexts().Contains(extensions::MenuItem::LAUNCHER);
34 }
35
36 }  // namespace
37
38 LauncherContextMenu::LauncherContextMenu(ChromeLauncherController* controller,
39                                          const ash::LauncherItem* item,
40                                          aura::Window* root)
41     : ui::SimpleMenuModel(NULL),
42       controller_(controller),
43       item_(*item),
44       shelf_alignment_menu_(root),
45       root_window_(root) {
46   DCHECK(item);
47   DCHECK(root_window_);
48   Init();
49 }
50
51 LauncherContextMenu::LauncherContextMenu(ChromeLauncherController* controller,
52                                          aura::Window* root)
53     : ui::SimpleMenuModel(NULL),
54       controller_(controller),
55       item_(ash::LauncherItem()),
56       shelf_alignment_menu_(root),
57       extension_items_(new extensions::ContextMenuMatcher(
58           controller->profile(), this, this,
59           base::Bind(MenuItemHasLauncherContext))),
60       root_window_(root) {
61   DCHECK(root_window_);
62   Init();
63 }
64
65 void LauncherContextMenu::Init() {
66   extension_items_.reset(new extensions::ContextMenuMatcher(
67       controller_->profile(), this, this,
68       base::Bind(MenuItemHasLauncherContext)));
69   set_delegate(this);
70
71   if (is_valid_item()) {
72     if (item_.type == ash::TYPE_APP_SHORTCUT ||
73         item_.type == ash::TYPE_WINDOWED_APP) {
74       // V1 apps can be started from the menu - but V2 apps should not.
75       if  (!controller_->IsPlatformApp(item_.id)) {
76         AddItem(MENU_OPEN_NEW, string16());
77         AddSeparator(ui::NORMAL_SEPARATOR);
78       }
79       AddItem(
80           MENU_PIN,
81           l10n_util::GetStringUTF16(controller_->IsPinned(item_.id) ?
82                                     IDS_LAUNCHER_CONTEXT_MENU_UNPIN :
83                                     IDS_LAUNCHER_CONTEXT_MENU_PIN));
84       if (controller_->IsOpen(item_.id)) {
85         AddItem(MENU_CLOSE,
86                 l10n_util::GetStringUTF16(IDS_LAUNCHER_CONTEXT_MENU_CLOSE));
87       }
88       if (!controller_->IsPlatformApp(item_.id) &&
89           item_.type != ash::TYPE_WINDOWED_APP) {
90         AddSeparator(ui::NORMAL_SEPARATOR);
91         AddCheckItemWithStringId(
92             LAUNCH_TYPE_REGULAR_TAB,
93             IDS_APP_CONTEXT_MENU_OPEN_REGULAR);
94         AddCheckItemWithStringId(
95             LAUNCH_TYPE_PINNED_TAB,
96             IDS_APP_CONTEXT_MENU_OPEN_PINNED);
97         AddCheckItemWithStringId(
98             LAUNCH_TYPE_WINDOW,
99             IDS_APP_CONTEXT_MENU_OPEN_WINDOW);
100         // Even though the launch type is Full Screen it is more accurately
101         // described as Maximized in Ash.
102         AddCheckItemWithStringId(
103             LAUNCH_TYPE_FULLSCREEN,
104             IDS_APP_CONTEXT_MENU_OPEN_MAXIMIZED);
105       }
106     } else if (item_.type == ash::TYPE_BROWSER_SHORTCUT) {
107       AddItem(MENU_NEW_WINDOW,
108               l10n_util::GetStringUTF16(IDS_LAUNCHER_NEW_WINDOW));
109       if (!controller_->IsLoggedInAsGuest()) {
110         AddItem(MENU_NEW_INCOGNITO_WINDOW,
111                 l10n_util::GetStringUTF16(IDS_LAUNCHER_NEW_INCOGNITO_WINDOW));
112       }
113     } else {
114       if (item_.type == ash::TYPE_PLATFORM_APP) {
115         AddItem(
116             MENU_PIN,
117             l10n_util::GetStringUTF16(IDS_LAUNCHER_CONTEXT_MENU_PIN));
118       }
119       if (controller_->IsOpen(item_.id)) {
120         AddItem(MENU_CLOSE,
121                 l10n_util::GetStringUTF16(IDS_LAUNCHER_CONTEXT_MENU_CLOSE));
122       }
123     }
124     AddSeparator(ui::NORMAL_SEPARATOR);
125     if (item_.type == ash::TYPE_APP_SHORTCUT ||
126         item_.type == ash::TYPE_WINDOWED_APP ||
127         item_.type == ash::TYPE_PLATFORM_APP) {
128       std::string app_id = controller_->GetAppIDForLauncherID(item_.id);
129       if (!app_id.empty()) {
130         int index = 0;
131         extension_items_->AppendExtensionItems(
132             app_id, string16(), &index);
133         AddSeparator(ui::NORMAL_SEPARATOR);
134       }
135     }
136   }
137   // In fullscreen, the launcher is either hidden or autohidden depending on
138   // the type of fullscreen. Do not show the auto-hide menu item while in
139   // fullscreen because it is confusing when the preference appears not to
140   // apply.
141   if (!IsFullScreenMode()) {
142     AddCheckItemWithStringId(MENU_AUTO_HIDE,
143                              IDS_ASH_SHELF_CONTEXT_MENU_AUTO_HIDE);
144   }
145   if (ash::ShelfWidget::ShelfAlignmentAllowed()) {
146     AddSubMenuWithStringId(MENU_ALIGNMENT_MENU,
147                            IDS_ASH_SHELF_CONTEXT_MENU_POSITION,
148                            &shelf_alignment_menu_);
149   }
150 #if defined(OS_CHROMEOS)
151   AddItem(MENU_CHANGE_WALLPAPER,
152        l10n_util::GetStringUTF16(IDS_AURA_SET_DESKTOP_WALLPAPER));
153 #endif
154 }
155
156 LauncherContextMenu::~LauncherContextMenu() {
157 }
158
159 bool LauncherContextMenu::IsItemForCommandIdDynamic(int command_id) const {
160   return command_id == MENU_OPEN_NEW;
161 }
162
163 string16 LauncherContextMenu::GetLabelForCommandId(int command_id) const {
164   if (command_id == MENU_OPEN_NEW) {
165     if (item_.type == ash::TYPE_PLATFORM_APP) {
166       return l10n_util::GetStringUTF16(IDS_LAUNCHER_CONTEXT_MENU_NEW_WINDOW);
167     }
168     switch (controller_->GetLaunchType(item_.id)) {
169       case extensions::ExtensionPrefs::LAUNCH_PINNED:
170       case extensions::ExtensionPrefs::LAUNCH_REGULAR:
171         return l10n_util::GetStringUTF16(IDS_LAUNCHER_CONTEXT_MENU_NEW_TAB);
172       case extensions::ExtensionPrefs::LAUNCH_FULLSCREEN:
173       case extensions::ExtensionPrefs::LAUNCH_WINDOW:
174         return l10n_util::GetStringUTF16(IDS_LAUNCHER_CONTEXT_MENU_NEW_WINDOW);
175     }
176   }
177   NOTREACHED();
178   return string16();
179 }
180
181 bool LauncherContextMenu::IsCommandIdChecked(int command_id) const {
182   switch (command_id) {
183     case LAUNCH_TYPE_PINNED_TAB:
184       return controller_->GetLaunchType(item_.id) ==
185           extensions::ExtensionPrefs::LAUNCH_PINNED;
186     case LAUNCH_TYPE_REGULAR_TAB:
187       return controller_->GetLaunchType(item_.id) ==
188           extensions::ExtensionPrefs::LAUNCH_REGULAR;
189     case LAUNCH_TYPE_WINDOW:
190       return controller_->GetLaunchType(item_.id) ==
191           extensions::ExtensionPrefs::LAUNCH_WINDOW;
192     case LAUNCH_TYPE_FULLSCREEN:
193       return controller_->GetLaunchType(item_.id) ==
194           extensions::ExtensionPrefs::LAUNCH_FULLSCREEN;
195     case MENU_AUTO_HIDE:
196       return controller_->GetShelfAutoHideBehavior(root_window_) ==
197           ash::SHELF_AUTO_HIDE_BEHAVIOR_ALWAYS;
198     default:
199       return extension_items_->IsCommandIdChecked(command_id);
200   }
201 }
202
203 bool LauncherContextMenu::IsCommandIdEnabled(int command_id) const {
204   switch (command_id) {
205     case MENU_PIN:
206       return controller_->IsPinnable(item_.id);
207 #if defined(OS_CHROMEOS)
208     case MENU_CHANGE_WALLPAPER:
209       return ash::Shell::GetInstance()->user_wallpaper_delegate()->
210           CanOpenSetWallpaperPage();
211 #endif
212     case MENU_NEW_WINDOW:
213       // "Normal" windows are not allowed when incognito is enforced.
214       return IncognitoModePrefs::GetAvailability(
215           controller_->profile()->GetPrefs()) != IncognitoModePrefs::FORCED;
216     case MENU_AUTO_HIDE:
217       return controller_->CanUserModifyShelfAutoHideBehavior(root_window_);
218     case MENU_NEW_INCOGNITO_WINDOW:
219       // Incognito windows are not allowed when incognito is disabled.
220       return IncognitoModePrefs::GetAvailability(
221           controller_->profile()->GetPrefs()) != IncognitoModePrefs::DISABLED;
222     default:
223       return extension_items_->IsCommandIdEnabled(command_id);
224   }
225 }
226
227 bool LauncherContextMenu::GetAcceleratorForCommandId(
228       int command_id,
229       ui::Accelerator* accelerator) {
230   return false;
231 }
232
233 void LauncherContextMenu::ExecuteCommand(int command_id, int event_flags) {
234   switch (static_cast<MenuItem>(command_id)) {
235     case MENU_OPEN_NEW:
236       controller_->Launch(item_.id, ui::EF_NONE);
237       break;
238     case MENU_CLOSE:
239       controller_->Close(item_.id);
240       ChromeShellDelegate::instance()->RecordUserMetricsAction(
241           ash::UMA_CLOSE_THROUGH_CONTEXT_MENU);
242       break;
243     case MENU_PIN:
244       controller_->TogglePinned(item_.id);
245       break;
246     case LAUNCH_TYPE_PINNED_TAB:
247       controller_->SetLaunchType(item_.id,
248                                  extensions::ExtensionPrefs::LAUNCH_PINNED);
249       break;
250     case LAUNCH_TYPE_REGULAR_TAB:
251       controller_->SetLaunchType(item_.id,
252                                  extensions::ExtensionPrefs::LAUNCH_REGULAR);
253       break;
254     case LAUNCH_TYPE_WINDOW:
255       controller_->SetLaunchType(item_.id,
256                                  extensions::ExtensionPrefs::LAUNCH_WINDOW);
257       break;
258     case LAUNCH_TYPE_FULLSCREEN:
259       controller_->SetLaunchType(item_.id,
260                                  extensions::ExtensionPrefs::LAUNCH_FULLSCREEN);
261       break;
262     case MENU_AUTO_HIDE:
263       controller_->ToggleShelfAutoHideBehavior(root_window_);
264       break;
265     case MENU_NEW_WINDOW:
266       controller_->CreateNewWindow();
267       break;
268     case MENU_NEW_INCOGNITO_WINDOW:
269       controller_->CreateNewIncognitoWindow();
270       break;
271     case MENU_ALIGNMENT_MENU:
272       break;
273 #if defined(OS_CHROMEOS)
274     case MENU_CHANGE_WALLPAPER:
275       ash::Shell::GetInstance()->user_wallpaper_delegate()->
276           OpenSetWallpaperPage();
277       break;
278 #endif
279     default:
280       extension_items_->ExecuteCommand(command_id, NULL,
281                                        content::ContextMenuParams());
282   }
283 }