Cleanup: json_schema_test.js now lives in extensions/test/data.
[chromium-blink-merge.git] / ash / accelerators / accelerator_controller.cc
blob5900769b909aead3aeef8258b0a2cb18ce52a25d
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.
5 #include "ash/accelerators/accelerator_controller.h"
7 #include <algorithm>
8 #include <cmath>
9 #include <string>
11 #include "ash/accelerators/accelerator_commands.h"
12 #include "ash/accelerators/debug_commands.h"
13 #include "ash/ash_switches.h"
14 #include "ash/debug.h"
15 #include "ash/display/display_controller.h"
16 #include "ash/display/display_manager.h"
17 #include "ash/display/display_util.h"
18 #include "ash/focus_cycler.h"
19 #include "ash/gpu_support.h"
20 #include "ash/ime_control_delegate.h"
21 #include "ash/magnifier/magnification_controller.h"
22 #include "ash/magnifier/partial_magnification_controller.h"
23 #include "ash/media_delegate.h"
24 #include "ash/multi_profile_uma.h"
25 #include "ash/new_window_delegate.h"
26 #include "ash/root_window_controller.h"
27 #include "ash/rotator/screen_rotation.h"
28 #include "ash/screenshot_delegate.h"
29 #include "ash/session/session_state_delegate.h"
30 #include "ash/shelf/shelf.h"
31 #include "ash/shelf/shelf_delegate.h"
32 #include "ash/shelf/shelf_model.h"
33 #include "ash/shelf/shelf_widget.h"
34 #include "ash/shell.h"
35 #include "ash/shell_delegate.h"
36 #include "ash/shell_window_ids.h"
37 #include "ash/system/brightness_control_delegate.h"
38 #include "ash/system/keyboard_brightness/keyboard_brightness_control_delegate.h"
39 #include "ash/system/status_area_widget.h"
40 #include "ash/system/tray/system_tray.h"
41 #include "ash/system/tray/system_tray_delegate.h"
42 #include "ash/system/tray/system_tray_notifier.h"
43 #include "ash/system/web_notification/web_notification_tray.h"
44 #include "ash/touch/touch_hud_debug.h"
45 #include "ash/utility/partial_screenshot_controller.h"
46 #include "ash/volume_control_delegate.h"
47 #include "ash/wm/maximize_mode/maximize_mode_controller.h"
48 #include "ash/wm/mru_window_tracker.h"
49 #include "ash/wm/overview/window_selector_controller.h"
50 #include "ash/wm/power_button_controller.h"
51 #include "ash/wm/window_cycle_controller.h"
52 #include "ash/wm/window_state.h"
53 #include "ash/wm/window_util.h"
54 #include "ash/wm/wm_event.h"
55 #include "base/bind.h"
56 #include "base/command_line.h"
57 #include "base/metrics/user_metrics.h"
58 #include "ui/aura/env.h"
59 #include "ui/base/accelerators/accelerator.h"
60 #include "ui/base/accelerators/accelerator_manager.h"
61 #include "ui/compositor/layer.h"
62 #include "ui/compositor/layer_animation_sequence.h"
63 #include "ui/compositor/layer_animator.h"
64 #include "ui/events/event.h"
65 #include "ui/events/keycodes/keyboard_codes.h"
66 #include "ui/gfx/screen.h"
67 #include "ui/views/controls/webview/webview.h"
69 #if defined(OS_CHROMEOS)
70 #include "ash/system/chromeos/keyboard_brightness_controller.h"
71 #include "base/sys_info.h"
72 #include "ui/base/ime/chromeos/ime_keyboard.h"
73 #include "ui/base/ime/chromeos/input_method_manager.h"
74 #endif // defined(OS_CHROMEOS)
76 namespace ash {
77 namespace {
79 using base::UserMetricsAction;
81 bool CanHandleAccessibleFocusCycle() {
82 if (!Shell::GetInstance()->accessibility_delegate()->
83 IsSpokenFeedbackEnabled()) {
84 return false;
86 aura::Window* active_window = ash::wm::GetActiveWindow();
87 if (!active_window)
88 return false;
89 views::Widget* widget =
90 views::Widget::GetWidgetForNativeWindow(active_window);
91 if (!widget)
92 return false;
93 views::FocusManager* focus_manager = widget->GetFocusManager();
94 if (!focus_manager)
95 return false;
96 views::View* view = focus_manager->GetFocusedView();
97 return view && strcmp(view->GetClassName(), views::WebView::kViewClassName);
100 void HandleAccessibleFocusCycle(bool reverse) {
101 if (reverse)
102 base::RecordAction(UserMetricsAction("Accel_Accessible_Focus_Previous"));
103 else
104 base::RecordAction(UserMetricsAction("Accel_Accessible_Focus_Next"));
106 aura::Window* active_window = ash::wm::GetActiveWindow();
107 views::Widget* widget =
108 views::Widget::GetWidgetForNativeWindow(active_window);
109 widget->GetFocusManager()->AdvanceFocus(reverse);
112 void HandleCycleBackwardMRU(const ui::Accelerator& accelerator) {
113 if (accelerator.key_code() == ui::VKEY_TAB)
114 base::RecordAction(base::UserMetricsAction("Accel_PrevWindow_Tab"));
116 Shell::GetInstance()->window_cycle_controller()->HandleCycleWindow(
117 WindowCycleController::BACKWARD);
120 void HandleCycleForwardMRU(const ui::Accelerator& accelerator) {
121 if (accelerator.key_code() == ui::VKEY_TAB)
122 base::RecordAction(base::UserMetricsAction("Accel_NextWindow_Tab"));
124 Shell::GetInstance()->window_cycle_controller()->HandleCycleWindow(
125 WindowCycleController::FORWARD);
128 void HandleRotatePaneFocus(Shell::Direction direction) {
129 Shell* shell = Shell::GetInstance();
130 switch (direction) {
131 // TODO(stevet): Not sure if this is the same as IDC_FOCUS_NEXT_PANE.
132 case Shell::FORWARD: {
133 base::RecordAction(UserMetricsAction("Accel_Focus_Next_Pane"));
134 shell->focus_cycler()->RotateFocus(FocusCycler::FORWARD);
135 break;
137 case Shell::BACKWARD: {
138 base::RecordAction(UserMetricsAction("Accel_Focus_Previous_Pane"));
139 shell->focus_cycler()->RotateFocus(FocusCycler::BACKWARD);
140 break;
145 void HandleFocusShelf() {
146 Shell* shell = Shell::GetInstance();
147 base::RecordAction(base::UserMetricsAction("Accel_Focus_Shelf"));
148 shell->focus_cycler()->FocusWidget(
149 Shelf::ForPrimaryDisplay()->shelf_widget());
152 void HandleLaunchAppN(int n) {
153 base::RecordAction(UserMetricsAction("Accel_Launch_App"));
154 Shelf::ForPrimaryDisplay()->LaunchAppIndexAt(n);
157 void HandleLaunchLastApp() {
158 base::RecordAction(UserMetricsAction("Accel_Launch_Last_App"));
159 Shelf::ForPrimaryDisplay()->LaunchAppIndexAt(-1);
162 bool CanHandleMagnifyScreen() {
163 Shell* shell = Shell::GetInstance();
164 return shell->magnification_controller()->IsEnabled() ||
165 shell->partial_magnification_controller()->is_enabled();
168 // Magnify the screen
169 void HandleMagnifyScreen(int delta_index) {
170 if (ash::Shell::GetInstance()->magnification_controller()->IsEnabled()) {
171 // TODO(yoshiki): Move the following logic to MagnificationController.
172 float scale =
173 ash::Shell::GetInstance()->magnification_controller()->GetScale();
174 // Calculate rounded logarithm (base kMagnificationScaleFactor) of scale.
175 int scale_index = std::floor(
176 std::log(scale) / std::log(ui::kMagnificationScaleFactor) + 0.5);
178 int new_scale_index = std::max(0, std::min(8, scale_index + delta_index));
180 ash::Shell::GetInstance()->magnification_controller()->SetScale(
181 std::pow(ui::kMagnificationScaleFactor, new_scale_index), true);
182 } else if (ash::Shell::GetInstance()->
183 partial_magnification_controller()->is_enabled()) {
184 float scale = delta_index > 0 ? kDefaultPartialMagnifiedScale : 1;
185 ash::Shell::GetInstance()->partial_magnification_controller()->
186 SetScale(scale);
190 void HandleMediaNextTrack() {
191 Shell::GetInstance()->media_delegate()->HandleMediaNextTrack();
194 void HandleMediaPlayPause() {
195 Shell::GetInstance()->media_delegate()->HandleMediaPlayPause();
198 void HandleMediaPrevTrack() {
199 Shell::GetInstance()->media_delegate()->HandleMediaPrevTrack();
202 bool CanHandleNewIncognitoWindow() {
203 return Shell::GetInstance()->delegate()->IsIncognitoAllowed();
206 void HandleNewIncognitoWindow() {
207 base::RecordAction(UserMetricsAction("Accel_New_Incognito_Window"));
208 Shell::GetInstance()->new_window_delegate()->NewWindow(
209 true /* is_incognito */);
212 void HandleNewTab(const ui::Accelerator& accelerator) {
213 if (accelerator.key_code() == ui::VKEY_T)
214 base::RecordAction(base::UserMetricsAction("Accel_NewTab_T"));
215 Shell::GetInstance()->new_window_delegate()->NewTab();
218 void HandleNewWindow() {
219 base::RecordAction(base::UserMetricsAction("Accel_New_Window"));
220 Shell::GetInstance()->new_window_delegate()->NewWindow(
221 false /* is_incognito */);
224 bool CanHandleNextIme(ImeControlDelegate* ime_control_delegate,
225 const ui::Accelerator& previous_accelerator) {
226 // This check is necessary e.g. not to process the Shift+Alt+
227 // ET_KEY_RELEASED accelerator for Chrome OS (see ash/accelerators/
228 // accelerator_controller.cc) when Shift+Alt+Tab is pressed and then Tab
229 // is released.
230 ui::KeyboardCode previous_key_code = previous_accelerator.key_code();
231 if (previous_accelerator.type() == ui::ET_KEY_RELEASED &&
232 // Workaround for crbug.com/139556. CJK IME users tend to press
233 // Enter (or Space) and Shift+Alt almost at the same time to commit
234 // an IME string and then switch from the IME to the English layout.
235 // This workaround allows the user to trigger NEXT_IME even if the
236 // user presses Shift+Alt before releasing Enter.
237 // TODO(nona|mazda): Fix crbug.com/139556 in a cleaner way.
238 previous_key_code != ui::VKEY_RETURN &&
239 previous_key_code != ui::VKEY_SPACE) {
240 // We totally ignore this accelerator.
241 // TODO(mazda): Fix crbug.com/158217
242 return false;
244 return ime_control_delegate && ime_control_delegate->CanCycleIme();
247 void HandleNextIme(ImeControlDelegate* ime_control_delegate) {
248 base::RecordAction(UserMetricsAction("Accel_Next_Ime"));
249 ime_control_delegate->HandleNextIme();
252 void HandleOpenFeedbackPage() {
253 base::RecordAction(UserMetricsAction("Accel_Open_Feedback_Page"));
254 ash::Shell::GetInstance()->new_window_delegate()->OpenFeedbackPage();
257 bool CanHandlePreviousIme(ImeControlDelegate* ime_control_delegate) {
258 return ime_control_delegate && ime_control_delegate->CanCycleIme();
261 void HandlePreviousIme(ImeControlDelegate* ime_control_delegate,
262 const ui::Accelerator& accelerator) {
263 base::RecordAction(UserMetricsAction("Accel_Previous_Ime"));
264 if (accelerator.type() == ui::ET_KEY_PRESSED)
265 ime_control_delegate->HandlePreviousIme();
266 // Else: consume the Ctrl+Space ET_KEY_RELEASED event but do not do anything.
269 void HandleRestoreTab() {
270 base::RecordAction(base::UserMetricsAction("Accel_Restore_Tab"));
271 Shell::GetInstance()->new_window_delegate()->RestoreTab();
274 gfx::Display::Rotation GetNextRotation(gfx::Display::Rotation current) {
275 switch (current) {
276 case gfx::Display::ROTATE_0:
277 return gfx::Display::ROTATE_90;
278 case gfx::Display::ROTATE_90:
279 return gfx::Display::ROTATE_180;
280 case gfx::Display::ROTATE_180:
281 return gfx::Display::ROTATE_270;
282 case gfx::Display::ROTATE_270:
283 return gfx::Display::ROTATE_0;
285 NOTREACHED() << "Unknown rotation:" << current;
286 return gfx::Display::ROTATE_0;
289 // Rotates the screen.
290 void HandleRotateScreen() {
291 base::RecordAction(UserMetricsAction("Accel_Rotate_Window"));
292 gfx::Point point = Shell::GetScreen()->GetCursorScreenPoint();
293 gfx::Display display = Shell::GetScreen()->GetDisplayNearestPoint(point);
294 const DisplayInfo& display_info =
295 Shell::GetInstance()->display_manager()->GetDisplayInfo(display.id());
296 Shell::GetInstance()->display_manager()->SetDisplayRotation(
297 display.id(), GetNextRotation(display_info.rotation()));
300 // Rotate the active window.
301 void HandleRotateActiveWindow() {
302 base::RecordAction(UserMetricsAction("Accel_Rotate_Window"));
303 aura::Window* active_window = wm::GetActiveWindow();
304 if (active_window) {
305 // The rotation animation bases its target transform on the current
306 // rotation and position. Since there could be an animation in progress
307 // right now, queue this animation so when it starts it picks up a neutral
308 // rotation and position. Use replace so we only enqueue one at a time.
309 active_window->layer()->GetAnimator()->
310 set_preemption_strategy(ui::LayerAnimator::REPLACE_QUEUED_ANIMATIONS);
311 active_window->layer()->GetAnimator()->StartAnimation(
312 new ui::LayerAnimationSequence(
313 new ash::ScreenRotation(360, active_window->layer())));
317 bool CanHandleScaleReset() {
318 DisplayManager* display_manager = Shell::GetInstance()->display_manager();
319 int64 display_id = display_manager->GetDisplayIdForUIScaling();
320 return (display_id != gfx::Display::kInvalidDisplayID &&
321 display_manager->GetDisplayInfo(display_id).configured_ui_scale() !=
322 1.0f);
325 void HandleScaleReset() {
326 base::RecordAction(UserMetricsAction("Accel_Scale_Ui_Reset"));
327 DisplayManager* display_manager = Shell::GetInstance()->display_manager();
328 int64 display_id = display_manager->GetDisplayIdForUIScaling();
329 display_manager->SetDisplayUIScale(display_id, 1.0f);
332 bool CanHandleScaleUI() {
333 DisplayManager* display_manager = Shell::GetInstance()->display_manager();
334 int64 display_id = display_manager->GetDisplayIdForUIScaling();
335 return display_id != gfx::Display::kInvalidDisplayID;
338 void HandleScaleUI(bool up) {
339 DisplayManager* display_manager = Shell::GetInstance()->display_manager();
340 int64 display_id = display_manager->GetDisplayIdForUIScaling();
342 if (up) {
343 base::RecordAction(UserMetricsAction("Accel_Scale_Ui_Up"));
344 } else {
345 base::RecordAction(UserMetricsAction("Accel_Scale_Ui_Down"));
348 const DisplayInfo& display_info = display_manager->GetDisplayInfo(display_id);
349 float next_scale = GetNextUIScale(display_info, up);
350 display_manager->SetDisplayUIScale(display_id, next_scale);
353 void HandleShowKeyboardOverlay() {
354 base::RecordAction(UserMetricsAction("Accel_Show_Keyboard_Overlay"));
355 ash::Shell::GetInstance()->new_window_delegate()->ShowKeyboardOverlay();
358 bool CanHandleShowMessageCenterBubble() {
359 RootWindowController* controller =
360 RootWindowController::ForTargetRootWindow();
361 StatusAreaWidget* status_area_widget =
362 controller->shelf()->status_area_widget();
363 return status_area_widget &&
364 status_area_widget->web_notification_tray()->visible();
367 void HandleShowMessageCenterBubble() {
368 base::RecordAction(UserMetricsAction("Accel_Show_Message_Center_Bubble"));
369 RootWindowController* controller =
370 RootWindowController::ForTargetRootWindow();
371 StatusAreaWidget* status_area_widget =
372 controller->shelf()->status_area_widget();
373 if (status_area_widget) {
374 WebNotificationTray* notification_tray =
375 status_area_widget->web_notification_tray();
376 if (notification_tray->visible())
377 notification_tray->ShowMessageCenterBubble();
381 void HandleShowSystemTrayBubble() {
382 base::RecordAction(UserMetricsAction("Accel_Show_System_Tray_Bubble"));
383 RootWindowController* controller =
384 RootWindowController::ForTargetRootWindow();
385 if (!controller->GetSystemTray()->HasSystemBubble())
386 controller->GetSystemTray()->ShowDefaultView(BUBBLE_CREATE_NEW);
389 void HandleShowTaskManager() {
390 base::RecordAction(UserMetricsAction("Accel_Show_Task_Manager"));
391 Shell::GetInstance()->new_window_delegate()->ShowTaskManager();
394 bool CanHandleSwitchIme(ImeControlDelegate* ime_control_delegate,
395 const ui::Accelerator& accelerator) {
396 return ime_control_delegate &&
397 ime_control_delegate->CanSwitchIme(accelerator);
400 void HandleSwitchIme(ImeControlDelegate* ime_control_delegate,
401 const ui::Accelerator& accelerator) {
402 base::RecordAction(UserMetricsAction("Accel_Switch_Ime"));
403 ime_control_delegate->HandleSwitchIme(accelerator);
406 void HandleTakePartialScreenshot(ScreenshotDelegate* screenshot_delegate) {
407 base::RecordAction(UserMetricsAction("Accel_Take_Partial_Screenshot"));
408 if (screenshot_delegate) {
409 ash::PartialScreenshotController::StartPartialScreenshotSession(
410 screenshot_delegate);
414 void HandleTakeScreenshot(ScreenshotDelegate* screenshot_delegate) {
415 base::RecordAction(UserMetricsAction("Accel_Take_Screenshot"));
416 if (screenshot_delegate &&
417 screenshot_delegate->CanTakeScreenshot()) {
418 screenshot_delegate->HandleTakeScreenshotForAllRootWindows();
422 bool CanHandleToggleAppList(const ui::Accelerator& accelerator,
423 const ui::Accelerator& previous_accelerator) {
424 if (accelerator.key_code() == ui::VKEY_LWIN) {
425 // If something else was pressed between the Search key (LWIN)
426 // being pressed and released, then ignore the release of the
427 // Search key.
428 if (previous_accelerator.type() != ui::ET_KEY_PRESSED ||
429 previous_accelerator.key_code() != ui::VKEY_LWIN) {
430 return false;
433 // When spoken feedback is enabled, we should neither toggle the list nor
434 // consume the key since Search+Shift is one of the shortcuts the a11y
435 // feature uses. crbug.com/132296
436 if (Shell::GetInstance()
437 ->accessibility_delegate()
438 ->IsSpokenFeedbackEnabled()) {
439 return false;
442 return true;
445 void HandleToggleAppList(const ui::Accelerator& accelerator) {
446 if (accelerator.key_code() == ui::VKEY_LWIN)
447 base::RecordAction(base::UserMetricsAction("Accel_Search_LWin"));
448 ash::Shell::GetInstance()->ToggleAppList(NULL);
451 void HandleToggleFullscreen(const ui::Accelerator& accelerator) {
452 if (accelerator.key_code() == ui::VKEY_MEDIA_LAUNCH_APP2)
453 base::RecordAction(UserMetricsAction("Accel_Fullscreen_F4"));
454 accelerators::ToggleFullscreen();
457 void HandleToggleOverview() {
458 base::RecordAction(base::UserMetricsAction("Accel_Overview_F5"));
459 Shell::GetInstance()->window_selector_controller()->ToggleOverview();
462 bool CanHandleWindowSnapOrDock() {
463 wm::WindowState* window_state = wm::GetActiveWindowState();
464 // Disable window snapping shortcut key for full screen window due to
465 // http://crbug.com/135487.
466 return (window_state &&
467 (window_state->window()->type() == ui::wm::WINDOW_TYPE_NORMAL ||
468 window_state->window()->type() == ui::wm::WINDOW_TYPE_PANEL) &&
469 !window_state->IsFullscreen());
472 void HandleWindowSnapOrDock(AcceleratorAction action) {
473 if (action == WINDOW_CYCLE_SNAP_DOCK_LEFT)
474 base::RecordAction(UserMetricsAction("Accel_Window_Snap_Left"));
475 else
476 base::RecordAction(UserMetricsAction("Accel_Window_Snap_Right"));
478 const wm::WMEvent event(action == WINDOW_CYCLE_SNAP_DOCK_LEFT ?
479 wm::WM_EVENT_CYCLE_SNAP_DOCK_LEFT :
480 wm::WM_EVENT_CYCLE_SNAP_DOCK_RIGHT);
481 wm::GetActiveWindowState()->OnWMEvent(&event);
484 void HandleWindowMinimize() {
485 base::RecordAction(
486 base::UserMetricsAction("Accel_Toggle_Minimized_Minus"));
487 accelerators::ToggleMinimized();
490 bool CanHandlePositionCenter() {
491 // Docked windows do not support centering.
492 wm::WindowState* window_state = wm::GetActiveWindowState();
493 return (window_state && !window_state->IsDocked());
496 void HandlePositionCenter() {
497 base::RecordAction(UserMetricsAction("Accel_Window_Position_Center"));
498 wm::CenterWindow(wm::GetActiveWindow());
501 #if defined(OS_CHROMEOS)
502 void HandleBrightnessDown(BrightnessControlDelegate* delegate,
503 const ui::Accelerator& accelerator) {
504 if (delegate)
505 delegate->HandleBrightnessDown(accelerator);
508 void HandleBrightnessUp(BrightnessControlDelegate* delegate,
509 const ui::Accelerator& accelerator) {
510 if (delegate)
511 delegate->HandleBrightnessUp(accelerator);
514 bool CanHandleDisableCapsLock(const ui::Accelerator& previous_accelerator) {
515 ui::KeyboardCode previous_key_code = previous_accelerator.key_code();
516 if (previous_accelerator.type() == ui::ET_KEY_RELEASED ||
517 (previous_key_code != ui::VKEY_LSHIFT &&
518 previous_key_code != ui::VKEY_SHIFT &&
519 previous_key_code != ui::VKEY_RSHIFT)) {
520 // If something else was pressed between the Shift key being pressed
521 // and released, then ignore the release of the Shift key.
522 return false;
524 chromeos::input_method::InputMethodManager* ime =
525 chromeos::input_method::InputMethodManager::Get();
526 chromeos::input_method::ImeKeyboard* keyboard =
527 ime ? ime->GetImeKeyboard() : NULL;
528 return (keyboard && keyboard->CapsLockIsEnabled());
531 void HandleDisableCapsLock() {
532 base::RecordAction(UserMetricsAction("Accel_Disable_Caps_Lock"));
533 chromeos::input_method::InputMethodManager* ime =
534 chromeos::input_method::InputMethodManager::Get();
535 ime->GetImeKeyboard()->SetCapsLockEnabled(false);
538 void HandleKeyboardBrightnessDown(KeyboardBrightnessControlDelegate* delegate,
539 const ui::Accelerator& accelerator) {
540 if (delegate)
541 delegate->HandleKeyboardBrightnessDown(accelerator);
544 void HandleKeyboardBrightnessUp(KeyboardBrightnessControlDelegate* delegate,
545 const ui::Accelerator& accelerator) {
546 if (delegate)
547 delegate->HandleKeyboardBrightnessUp(accelerator);
550 void HandleLock() {
551 base::RecordAction(UserMetricsAction("Accel_LockScreen_L"));
552 Shell::GetInstance()->session_state_delegate()->LockScreen();
555 void HandleCrosh() {
556 base::RecordAction(UserMetricsAction("Accel_Open_Crosh"));
558 Shell::GetInstance()->new_window_delegate()->OpenCrosh();
561 void HandleFileManager() {
562 base::RecordAction(UserMetricsAction("Accel_Open_File_Manager"));
564 Shell::GetInstance()->new_window_delegate()->OpenFileManager();
567 void HandleGetHelp() {
568 Shell::GetInstance()->new_window_delegate()->OpenGetHelp();
571 bool CanHandleSilenceSpokenFeedback() {
572 AccessibilityDelegate* delegate =
573 Shell::GetInstance()->accessibility_delegate();
574 return delegate->IsSpokenFeedbackEnabled();
577 void HandleSilenceSpokenFeedback() {
578 base::RecordAction(UserMetricsAction("Accel_Silence_Spoken_Feedback"));
579 Shell::GetInstance()->accessibility_delegate()->SilenceSpokenFeedback();
582 void HandleSwapPrimaryDisplay() {
583 base::RecordAction(UserMetricsAction("Accel_Swap_Primary_Display"));
584 Shell::GetInstance()->display_controller()->SwapPrimaryDisplay();
587 bool CanHandleCycleUser() {
588 Shell* shell = Shell::GetInstance();
589 return shell->delegate()->IsMultiProfilesEnabled() &&
590 shell->session_state_delegate()->NumberOfLoggedInUsers() > 1;
593 void HandleCycleUser(SessionStateDelegate::CycleUser cycle_user) {
594 MultiProfileUMA::RecordSwitchActiveUser(
595 MultiProfileUMA::SWITCH_ACTIVE_USER_BY_ACCELERATOR);
596 switch (cycle_user) {
597 case SessionStateDelegate::CYCLE_TO_NEXT_USER:
598 base::RecordAction(UserMetricsAction("Accel_Switch_To_Next_User"));
599 break;
600 case SessionStateDelegate::CYCLE_TO_PREVIOUS_USER:
601 base::RecordAction(UserMetricsAction("Accel_Switch_To_Previous_User"));
602 break;
604 Shell::GetInstance()->session_state_delegate()->CycleActiveUser(cycle_user);
607 bool CanHandleToggleCapsLock(const ui::Accelerator& accelerator,
608 const ui::Accelerator& previous_accelerator) {
609 if (accelerator.key_code() == ui::VKEY_LWIN) {
610 // If something else was pressed between the Search key (LWIN)
611 // being pressed and released, then ignore the release of the
612 // Search key.
613 // TODO(danakj): Releasing Alt first breaks this: crbug.com/166495
614 if (previous_accelerator.type() == ui::ET_KEY_RELEASED ||
615 previous_accelerator.key_code() != ui::VKEY_LWIN)
616 return false;
618 chromeos::input_method::InputMethodManager* ime =
619 chromeos::input_method::InputMethodManager::Get();
620 return ime && ime->GetImeKeyboard();
623 void HandleToggleCapsLock() {
624 base::RecordAction(UserMetricsAction("Accel_Toggle_Caps_Lock"));
625 chromeos::input_method::InputMethodManager* ime =
626 chromeos::input_method::InputMethodManager::Get();
627 chromeos::input_method::ImeKeyboard* keyboard = ime->GetImeKeyboard();
628 keyboard->SetCapsLockEnabled(!keyboard->CapsLockIsEnabled());
631 void HandleToggleMirrorMode() {
632 base::RecordAction(UserMetricsAction("Accel_Toggle_Mirror_Mode"));
633 Shell::GetInstance()->display_controller()->ToggleMirrorMode();
636 void HandleToggleSpokenFeedback() {
637 base::RecordAction(UserMetricsAction("Accel_Toggle_Spoken_Feedback"));
639 Shell::GetInstance()->accessibility_delegate()->
640 ToggleSpokenFeedback(ui::A11Y_NOTIFICATION_SHOW);
643 bool CanHandleToggleTouchViewTesting() {
644 return base::CommandLine::ForCurrentProcess()->HasSwitch(
645 switches::kAshEnableTouchViewTesting);
648 void HandleToggleTouchViewTesting() {
649 // TODO(skuhne): This is only temporary! Remove this!
650 MaximizeModeController* controller = Shell::GetInstance()->
651 maximize_mode_controller();
652 controller->EnableMaximizeModeWindowManager(
653 !controller->IsMaximizeModeWindowManagerEnabled());
656 bool CanHandleTouchHud() {
657 return RootWindowController::ForTargetRootWindow()->touch_hud_debug();
660 void HandleTouchHudClear() {
661 RootWindowController::ForTargetRootWindow()->touch_hud_debug()->Clear();
664 void HandleTouchHudModeChange() {
665 RootWindowController* controller =
666 RootWindowController::ForTargetRootWindow();
667 controller->touch_hud_debug()->ChangeToNextMode();
670 void HandleVolumeDown(const ui::Accelerator& accelerator) {
671 VolumeControlDelegate* volume_delegate =
672 Shell::GetInstance()->system_tray_delegate()->GetVolumeControlDelegate();
673 if (volume_delegate)
674 volume_delegate->HandleVolumeDown(accelerator);
677 void HandleVolumeMute(const ui::Accelerator& accelerator) {
678 VolumeControlDelegate* volume_delegate =
679 Shell::GetInstance()->system_tray_delegate()->GetVolumeControlDelegate();
680 if (volume_delegate)
681 volume_delegate->HandleVolumeMute(accelerator);
684 void HandleVolumeUp(const ui::Accelerator& accelerator) {
685 VolumeControlDelegate* volume_delegate =
686 Shell::GetInstance()->system_tray_delegate()->GetVolumeControlDelegate();
687 if (volume_delegate)
688 volume_delegate->HandleVolumeUp(accelerator);
691 #endif // defined(OS_CHROMEOS)
693 } // namespace
695 ////////////////////////////////////////////////////////////////////////////////
696 // AcceleratorController, public:
698 AcceleratorController::AcceleratorController()
699 : accelerator_manager_(new ui::AcceleratorManager),
700 accelerator_history_(new ui::AcceleratorHistory) {
701 Init();
704 AcceleratorController::~AcceleratorController() {
707 void AcceleratorController::Register(const ui::Accelerator& accelerator,
708 ui::AcceleratorTarget* target) {
709 accelerator_manager_->Register(accelerator,
710 ui::AcceleratorManager::kNormalPriority,
711 target);
714 void AcceleratorController::Unregister(const ui::Accelerator& accelerator,
715 ui::AcceleratorTarget* target) {
716 accelerator_manager_->Unregister(accelerator, target);
719 void AcceleratorController::UnregisterAll(ui::AcceleratorTarget* target) {
720 accelerator_manager_->UnregisterAll(target);
723 bool AcceleratorController::Process(const ui::Accelerator& accelerator) {
724 if (ime_control_delegate_) {
725 return accelerator_manager_->Process(
726 ime_control_delegate_->RemapAccelerator(accelerator));
728 return accelerator_manager_->Process(accelerator);
731 bool AcceleratorController::IsRegistered(
732 const ui::Accelerator& accelerator) const {
733 return accelerator_manager_->GetCurrentTarget(accelerator) != NULL;
736 bool AcceleratorController::IsPreferred(
737 const ui::Accelerator& accelerator) const {
738 const ui::Accelerator remapped_accelerator = ime_control_delegate_.get() ?
739 ime_control_delegate_->RemapAccelerator(accelerator) : accelerator;
741 std::map<ui::Accelerator, AcceleratorAction>::const_iterator iter =
742 accelerators_.find(remapped_accelerator);
743 if (iter == accelerators_.end())
744 return false; // not an accelerator.
746 return preferred_actions_.find(iter->second) != preferred_actions_.end();
749 bool AcceleratorController::IsReserved(
750 const ui::Accelerator& accelerator) const {
751 const ui::Accelerator remapped_accelerator = ime_control_delegate_.get() ?
752 ime_control_delegate_->RemapAccelerator(accelerator) : accelerator;
754 std::map<ui::Accelerator, AcceleratorAction>::const_iterator iter =
755 accelerators_.find(remapped_accelerator);
756 if (iter == accelerators_.end())
757 return false; // not an accelerator.
759 return reserved_actions_.find(iter->second) != reserved_actions_.end();
762 bool AcceleratorController::PerformActionIfEnabled(AcceleratorAction action) {
763 if (CanPerformAction(action, ui::Accelerator())) {
764 PerformAction(action, ui::Accelerator());
765 return true;
767 return false;
770 AcceleratorController::AcceleratorProcessingRestriction
771 AcceleratorController::GetCurrentAcceleratorRestriction() {
772 return GetAcceleratorProcessingRestriction(-1);
775 void AcceleratorController::SetBrightnessControlDelegate(
776 scoped_ptr<BrightnessControlDelegate> brightness_control_delegate) {
777 brightness_control_delegate_ = brightness_control_delegate.Pass();
780 void AcceleratorController::SetImeControlDelegate(
781 scoped_ptr<ImeControlDelegate> ime_control_delegate) {
782 ime_control_delegate_ = ime_control_delegate.Pass();
785 void AcceleratorController::SetScreenshotDelegate(
786 scoped_ptr<ScreenshotDelegate> screenshot_delegate) {
787 screenshot_delegate_ = screenshot_delegate.Pass();
790 ////////////////////////////////////////////////////////////////////////////////
791 // AcceleratorController, ui::AcceleratorTarget implementation:
793 bool AcceleratorController::AcceleratorPressed(
794 const ui::Accelerator& accelerator) {
795 std::map<ui::Accelerator, AcceleratorAction>::const_iterator it =
796 accelerators_.find(accelerator);
797 DCHECK(it != accelerators_.end());
798 AcceleratorAction action = it->second;
799 if (CanPerformAction(action, accelerator)) {
800 PerformAction(action, accelerator);
801 return ShouldActionConsumeKeyEvent(action);
803 return false;
806 bool AcceleratorController::CanHandleAccelerators() const {
807 return true;
810 ///////////////////////////////////////////////////////////////////////////////
811 // AcceleratorController, private:
813 void AcceleratorController::Init() {
814 for (size_t i = 0; i < kActionsAllowedAtLoginOrLockScreenLength; ++i) {
815 actions_allowed_at_login_screen_.insert(
816 kActionsAllowedAtLoginOrLockScreen[i]);
817 actions_allowed_at_lock_screen_.insert(
818 kActionsAllowedAtLoginOrLockScreen[i]);
820 for (size_t i = 0; i < kActionsAllowedAtLockScreenLength; ++i)
821 actions_allowed_at_lock_screen_.insert(kActionsAllowedAtLockScreen[i]);
822 for (size_t i = 0; i < kActionsAllowedAtModalWindowLength; ++i)
823 actions_allowed_at_modal_window_.insert(kActionsAllowedAtModalWindow[i]);
824 for (size_t i = 0; i < kPreferredActionsLength; ++i)
825 preferred_actions_.insert(kPreferredActions[i]);
826 for (size_t i = 0; i < kReservedActionsLength; ++i)
827 reserved_actions_.insert(kReservedActions[i]);
828 for (size_t i = 0; i < kNonrepeatableActionsLength; ++i)
829 nonrepeatable_actions_.insert(kNonrepeatableActions[i]);
830 for (size_t i = 0; i < kActionsAllowedInAppModeLength; ++i)
831 actions_allowed_in_app_mode_.insert(kActionsAllowedInAppMode[i]);
832 for (size_t i = 0; i < kActionsNeedingWindowLength; ++i)
833 actions_needing_window_.insert(kActionsNeedingWindow[i]);
835 RegisterAccelerators(kAcceleratorData, kAcceleratorDataLength);
837 if (debug::DebugAcceleratorsEnabled()) {
838 RegisterAccelerators(kDebugAcceleratorData, kDebugAcceleratorDataLength);
839 // All debug accelerators are reserved.
840 for (size_t i = 0; i < kDebugAcceleratorDataLength; ++i)
841 reserved_actions_.insert(kDebugAcceleratorData[i].action);
844 #if defined(OS_CHROMEOS)
845 keyboard_brightness_control_delegate_.reset(
846 new KeyboardBrightnessController());
847 #endif
850 void AcceleratorController::RegisterAccelerators(
851 const AcceleratorData accelerators[],
852 size_t accelerators_length) {
853 for (size_t i = 0; i < accelerators_length; ++i) {
854 ui::Accelerator accelerator(accelerators[i].keycode,
855 accelerators[i].modifiers);
856 accelerator.set_type(accelerators[i].trigger_on_press ?
857 ui::ET_KEY_PRESSED : ui::ET_KEY_RELEASED);
858 Register(accelerator, this);
859 accelerators_.insert(
860 std::make_pair(accelerator, accelerators[i].action));
864 bool AcceleratorController::CanPerformAction(
865 AcceleratorAction action,
866 const ui::Accelerator& accelerator) {
867 AcceleratorProcessingRestriction restriction =
868 GetAcceleratorProcessingRestriction(action);
869 if (restriction != RESTRICTION_NONE)
870 return restriction == RESTRICTION_PREVENT_PROCESSING_AND_PROPAGATION;
872 const ui::Accelerator& previous_accelerator =
873 accelerator_history_->previous_accelerator();
875 // True should be returned if running |action| does something. Otherwise,
876 // false should be returned to give the web contents a chance at handling the
877 // accelerator.
878 switch (action) {
879 case ACCESSIBLE_FOCUS_NEXT:
880 case ACCESSIBLE_FOCUS_PREVIOUS:
881 return CanHandleAccessibleFocusCycle();
882 case DEBUG_PRINT_LAYER_HIERARCHY:
883 case DEBUG_PRINT_VIEW_HIERARCHY:
884 case DEBUG_PRINT_WINDOW_HIERARCHY:
885 case DEBUG_TOGGLE_DESKTOP_BACKGROUND_MODE:
886 case DEBUG_TOGGLE_DEVICE_SCALE_FACTOR:
887 case DEBUG_TOGGLE_ROOT_WINDOW_FULL_SCREEN:
888 case DEBUG_TOGGLE_SHOW_DEBUG_BORDERS:
889 case DEBUG_TOGGLE_SHOW_FPS_COUNTER:
890 case DEBUG_TOGGLE_SHOW_PAINT_RECTS:
891 return debug::DebugAcceleratorsEnabled();
892 case MAGNIFY_SCREEN_ZOOM_IN:
893 case MAGNIFY_SCREEN_ZOOM_OUT:
894 return CanHandleMagnifyScreen();
895 case NEW_INCOGNITO_WINDOW:
896 return CanHandleNewIncognitoWindow();
897 case NEXT_IME:
898 return CanHandleNextIme(ime_control_delegate_.get(),
899 previous_accelerator);
900 case PREVIOUS_IME:
901 return CanHandlePreviousIme(ime_control_delegate_.get());
902 case SCALE_UI_RESET:
903 return CanHandleScaleReset();
904 case SCALE_UI_UP:
905 case SCALE_UI_DOWN:
906 return CanHandleScaleUI();
907 case SHOW_MESSAGE_CENTER_BUBBLE:
908 return CanHandleShowMessageCenterBubble();
909 case SWITCH_IME:
910 return CanHandleSwitchIme(ime_control_delegate_.get(), accelerator);
911 case TOGGLE_APP_LIST:
912 return CanHandleToggleAppList(accelerator, previous_accelerator);
913 case WINDOW_CYCLE_SNAP_DOCK_LEFT:
914 case WINDOW_CYCLE_SNAP_DOCK_RIGHT:
915 return CanHandleWindowSnapOrDock();
916 case WINDOW_POSITION_CENTER:
917 return CanHandlePositionCenter();
918 #if defined(OS_CHROMEOS)
919 case DEBUG_ADD_REMOVE_DISPLAY:
920 return debug::DebugAcceleratorsEnabled();
921 case DISABLE_CAPS_LOCK:
922 return CanHandleDisableCapsLock(previous_accelerator);
923 case SILENCE_SPOKEN_FEEDBACK:
924 return CanHandleSilenceSpokenFeedback();
925 case SWITCH_TO_PREVIOUS_USER:
926 case SWITCH_TO_NEXT_USER:
927 return CanHandleCycleUser();
928 case TOGGLE_CAPS_LOCK:
929 return CanHandleToggleCapsLock(accelerator, previous_accelerator);
930 case TOGGLE_TOUCH_VIEW_TESTING:
931 return CanHandleToggleTouchViewTesting();
932 case TOUCH_HUD_CLEAR:
933 case TOUCH_HUD_MODE_CHANGE:
934 return CanHandleTouchHud();
935 #endif
937 case CYCLE_BACKWARD_MRU:
938 case CYCLE_FORWARD_MRU:
939 case EXIT:
940 case FOCUS_NEXT_PANE:
941 case FOCUS_PREVIOUS_PANE:
942 case FOCUS_SHELF:
943 case LAUNCH_APP_0:
944 case LAUNCH_APP_1:
945 case LAUNCH_APP_2:
946 case LAUNCH_APP_3:
947 case LAUNCH_APP_4:
948 case LAUNCH_APP_5:
949 case LAUNCH_APP_6:
950 case LAUNCH_APP_7:
951 case LAUNCH_LAST_APP:
952 case MEDIA_NEXT_TRACK:
953 case MEDIA_PLAY_PAUSE:
954 case MEDIA_PREV_TRACK:
955 case NEW_TAB:
956 case NEW_WINDOW:
957 case OPEN_FEEDBACK_PAGE:
958 case PRINT_UI_HIERARCHIES:
959 case RESTORE_TAB:
960 case ROTATE_SCREEN:
961 case ROTATE_WINDOW:
962 case SHOW_KEYBOARD_OVERLAY:
963 case SHOW_SYSTEM_TRAY_BUBBLE:
964 case SHOW_TASK_MANAGER:
965 case TAKE_PARTIAL_SCREENSHOT:
966 case TAKE_SCREENSHOT:
967 case TOGGLE_FULLSCREEN:
968 case TOGGLE_MAXIMIZED:
969 case TOGGLE_OVERVIEW:
970 case WINDOW_MINIMIZE:
971 #if defined(OS_CHROMEOS)
972 case BRIGHTNESS_DOWN:
973 case BRIGHTNESS_UP:
974 case DISABLE_GPU_WATCHDOG:
975 case KEYBOARD_BRIGHTNESS_DOWN:
976 case KEYBOARD_BRIGHTNESS_UP:
977 case LOCK_PRESSED:
978 case LOCK_RELEASED:
979 case LOCK_SCREEN:
980 case OPEN_CROSH:
981 case OPEN_FILE_MANAGER:
982 case OPEN_GET_HELP:
983 case POWER_PRESSED:
984 case POWER_RELEASED:
985 case SWAP_PRIMARY_DISPLAY:
986 case TOGGLE_MIRROR_MODE:
987 case TOGGLE_SPOKEN_FEEDBACK:
988 case TOGGLE_WIFI:
989 case TOUCH_HUD_PROJECTION_TOGGLE:
990 case VOLUME_DOWN:
991 case VOLUME_MUTE:
992 case VOLUME_UP:
993 #else
994 case DUMMY_FOR_RESERVED:
995 #endif
996 return true;
998 return false;
1001 void AcceleratorController::PerformAction(AcceleratorAction action,
1002 const ui::Accelerator& accelerator) {
1003 AcceleratorProcessingRestriction restriction =
1004 GetAcceleratorProcessingRestriction(action);
1005 if (restriction != RESTRICTION_NONE)
1006 return;
1008 if (nonrepeatable_actions_.find(action) != nonrepeatable_actions_.end() &&
1009 accelerator.IsRepeat()) {
1010 return;
1013 // If your accelerator invokes more than one line of code, please either
1014 // implement it in your module's controller code (like TOGGLE_MIRROR_MODE
1015 // below) or pull it into a HandleFoo() function above.
1016 switch (action) {
1017 case ACCESSIBLE_FOCUS_NEXT:
1018 HandleAccessibleFocusCycle(false);
1019 break;
1020 case ACCESSIBLE_FOCUS_PREVIOUS:
1021 HandleAccessibleFocusCycle(true);
1022 break;
1023 case CYCLE_BACKWARD_MRU:
1024 HandleCycleBackwardMRU(accelerator);
1025 break;
1026 case CYCLE_FORWARD_MRU:
1027 HandleCycleForwardMRU(accelerator);
1028 break;
1029 case DEBUG_PRINT_LAYER_HIERARCHY:
1030 case DEBUG_PRINT_VIEW_HIERARCHY:
1031 case DEBUG_PRINT_WINDOW_HIERARCHY:
1032 case DEBUG_TOGGLE_DESKTOP_BACKGROUND_MODE:
1033 case DEBUG_TOGGLE_DEVICE_SCALE_FACTOR:
1034 case DEBUG_TOGGLE_ROOT_WINDOW_FULL_SCREEN:
1035 case DEBUG_TOGGLE_SHOW_DEBUG_BORDERS:
1036 case DEBUG_TOGGLE_SHOW_FPS_COUNTER:
1037 case DEBUG_TOGGLE_SHOW_PAINT_RECTS:
1038 debug::PerformDebugActionIfEnabled(action);
1039 break;
1040 case EXIT:
1041 // UMA metrics are recorded in the handler.
1042 exit_warning_handler_.HandleAccelerator();
1043 break;
1044 case FOCUS_NEXT_PANE:
1045 HandleRotatePaneFocus(Shell::FORWARD);
1046 break;
1047 case FOCUS_PREVIOUS_PANE:
1048 HandleRotatePaneFocus(Shell::BACKWARD);
1049 break;
1050 case FOCUS_SHELF:
1051 HandleFocusShelf();
1052 break;
1053 case LAUNCH_APP_0:
1054 HandleLaunchAppN(0);
1055 break;
1056 case LAUNCH_APP_1:
1057 HandleLaunchAppN(1);
1058 break;
1059 case LAUNCH_APP_2:
1060 HandleLaunchAppN(2);
1061 break;
1062 case LAUNCH_APP_3:
1063 HandleLaunchAppN(3);
1064 break;
1065 case LAUNCH_APP_4:
1066 HandleLaunchAppN(4);
1067 break;
1068 case LAUNCH_APP_5:
1069 HandleLaunchAppN(5);
1070 break;
1071 case LAUNCH_APP_6:
1072 HandleLaunchAppN(6);
1073 break;
1074 case LAUNCH_APP_7:
1075 HandleLaunchAppN(7);
1076 break;
1077 case LAUNCH_LAST_APP:
1078 HandleLaunchLastApp();
1079 break;
1080 case MAGNIFY_SCREEN_ZOOM_IN:
1081 HandleMagnifyScreen(1);
1082 break;
1083 case MAGNIFY_SCREEN_ZOOM_OUT:
1084 HandleMagnifyScreen(-1);
1085 break;
1086 case MEDIA_NEXT_TRACK:
1087 HandleMediaNextTrack();
1088 break;
1089 case MEDIA_PLAY_PAUSE:
1090 HandleMediaPlayPause();
1091 break;
1092 case MEDIA_PREV_TRACK:
1093 HandleMediaPrevTrack();
1094 break;
1095 case NEW_INCOGNITO_WINDOW:
1096 HandleNewIncognitoWindow();
1097 break;
1098 case NEW_TAB:
1099 HandleNewTab(accelerator);
1100 break;
1101 case NEW_WINDOW:
1102 HandleNewWindow();
1103 break;
1104 case NEXT_IME:
1105 HandleNextIme(ime_control_delegate_.get());
1106 break;
1107 case OPEN_FEEDBACK_PAGE:
1108 HandleOpenFeedbackPage();
1109 break;
1110 case PREVIOUS_IME:
1111 HandlePreviousIme(ime_control_delegate_.get(), accelerator);
1112 break;
1113 case PRINT_UI_HIERARCHIES:
1114 debug::PrintUIHierarchies();
1115 break;
1116 case RESTORE_TAB:
1117 HandleRestoreTab();
1118 break;
1119 case ROTATE_SCREEN:
1120 HandleRotateScreen();
1121 break;
1122 case ROTATE_WINDOW:
1123 HandleRotateActiveWindow();
1124 break;
1125 case SCALE_UI_DOWN:
1126 HandleScaleUI(false /* down */);
1127 break;
1128 case SCALE_UI_RESET:
1129 HandleScaleReset();
1130 break;
1131 case SCALE_UI_UP:
1132 HandleScaleUI(true /* up */);
1133 break;
1134 case SHOW_KEYBOARD_OVERLAY:
1135 HandleShowKeyboardOverlay();
1136 break;
1137 case SHOW_MESSAGE_CENTER_BUBBLE:
1138 HandleShowMessageCenterBubble();
1139 break;
1140 case SHOW_SYSTEM_TRAY_BUBBLE:
1141 HandleShowSystemTrayBubble();
1142 break;
1143 case SHOW_TASK_MANAGER:
1144 HandleShowTaskManager();
1145 break;
1146 case SWITCH_IME:
1147 HandleSwitchIme(ime_control_delegate_.get(), accelerator);
1148 break;
1149 case TAKE_PARTIAL_SCREENSHOT:
1150 HandleTakePartialScreenshot(screenshot_delegate_.get());
1151 break;
1152 case TAKE_SCREENSHOT:
1153 HandleTakeScreenshot(screenshot_delegate_.get());
1154 break;
1155 case TOGGLE_APP_LIST:
1156 HandleToggleAppList(accelerator);
1157 break;
1158 case TOGGLE_FULLSCREEN:
1159 HandleToggleFullscreen(accelerator);
1160 break;
1161 case TOGGLE_MAXIMIZED:
1162 accelerators::ToggleMaximized();
1163 break;
1164 case TOGGLE_OVERVIEW:
1165 HandleToggleOverview();
1166 break;
1167 case WINDOW_CYCLE_SNAP_DOCK_LEFT:
1168 case WINDOW_CYCLE_SNAP_DOCK_RIGHT:
1169 HandleWindowSnapOrDock(action);
1170 break;
1171 case WINDOW_MINIMIZE:
1172 HandleWindowMinimize();
1173 break;
1174 case WINDOW_POSITION_CENTER:
1175 HandlePositionCenter();
1176 break;
1177 #if defined(OS_CHROMEOS)
1178 case BRIGHTNESS_DOWN:
1179 HandleBrightnessDown(brightness_control_delegate_.get(), accelerator);
1180 break;
1181 case BRIGHTNESS_UP:
1182 HandleBrightnessUp(brightness_control_delegate_.get(), accelerator);
1183 break;
1184 case DEBUG_ADD_REMOVE_DISPLAY:
1185 debug::PerformDebugActionIfEnabled(action);
1186 break;
1187 case DISABLE_CAPS_LOCK:
1188 HandleDisableCapsLock();
1189 break;
1190 case DISABLE_GPU_WATCHDOG:
1191 Shell::GetInstance()->gpu_support()->DisableGpuWatchdog();
1192 break;
1193 case KEYBOARD_BRIGHTNESS_DOWN:
1194 HandleKeyboardBrightnessDown(keyboard_brightness_control_delegate_.get(),
1195 accelerator);
1196 break;
1197 case KEYBOARD_BRIGHTNESS_UP:
1198 HandleKeyboardBrightnessUp(keyboard_brightness_control_delegate_.get(),
1199 accelerator);
1200 break;
1201 case LOCK_PRESSED:
1202 case LOCK_RELEASED:
1203 Shell::GetInstance()->power_button_controller()->
1204 OnLockButtonEvent(action == LOCK_PRESSED, base::TimeTicks());
1205 break;
1206 case LOCK_SCREEN:
1207 HandleLock();
1208 break;
1209 case OPEN_CROSH:
1210 HandleCrosh();
1211 break;
1212 case OPEN_FILE_MANAGER:
1213 HandleFileManager();
1214 break;
1215 case OPEN_GET_HELP:
1216 HandleGetHelp();
1217 break;
1218 case POWER_PRESSED: // fallthrough
1219 case POWER_RELEASED:
1220 if (!base::SysInfo::IsRunningOnChromeOS()) {
1221 // There is no powerd, the Chrome OS power manager, in linux desktop,
1222 // so call the PowerButtonController here.
1223 Shell::GetInstance()->power_button_controller()->
1224 OnPowerButtonEvent(action == POWER_PRESSED, base::TimeTicks());
1226 // We don't do anything with these at present on the device,
1227 // (power button events are reported to us from powerm via
1228 // D-BUS), but we consume them to prevent them from getting
1229 // passed to apps -- see http://crbug.com/146609.
1230 break;
1231 case SILENCE_SPOKEN_FEEDBACK:
1232 HandleSilenceSpokenFeedback();
1233 break;
1234 case SWAP_PRIMARY_DISPLAY:
1235 HandleSwapPrimaryDisplay();
1236 break;
1237 case SWITCH_TO_NEXT_USER:
1238 HandleCycleUser(SessionStateDelegate::CYCLE_TO_NEXT_USER);
1239 break;
1240 case SWITCH_TO_PREVIOUS_USER:
1241 HandleCycleUser(SessionStateDelegate::CYCLE_TO_PREVIOUS_USER);
1242 break;
1243 case TOGGLE_CAPS_LOCK:
1244 HandleToggleCapsLock();
1245 break;
1246 case TOGGLE_MIRROR_MODE:
1247 HandleToggleMirrorMode();
1248 break;
1249 case TOGGLE_SPOKEN_FEEDBACK:
1250 HandleToggleSpokenFeedback();
1251 break;
1252 case TOGGLE_TOUCH_VIEW_TESTING:
1253 HandleToggleTouchViewTesting();
1254 break;
1255 case TOGGLE_WIFI:
1256 Shell::GetInstance()->system_tray_notifier()->NotifyRequestToggleWifi();
1257 break;
1258 case TOUCH_HUD_CLEAR:
1259 HandleTouchHudClear();
1260 break;
1261 case TOUCH_HUD_MODE_CHANGE:
1262 HandleTouchHudModeChange();
1263 break;
1264 case TOUCH_HUD_PROJECTION_TOGGLE:
1265 accelerators::ToggleTouchHudProjection();
1266 break;
1267 case VOLUME_DOWN:
1268 HandleVolumeDown(accelerator);
1269 break;
1270 case VOLUME_MUTE:
1271 HandleVolumeMute(accelerator);
1272 break;
1273 case VOLUME_UP:
1274 HandleVolumeUp(accelerator);
1275 break;
1276 #else
1277 case DUMMY_FOR_RESERVED:
1278 NOTREACHED();
1279 break;
1280 #endif
1284 bool AcceleratorController::ShouldActionConsumeKeyEvent(
1285 AcceleratorAction action) {
1286 #if defined(OS_CHROMEOS)
1287 if (action == SILENCE_SPOKEN_FEEDBACK)
1288 return false;
1289 #endif
1291 // Adding new exceptions is *STRONGLY* discouraged.
1292 return true;
1295 AcceleratorController::AcceleratorProcessingRestriction
1296 AcceleratorController::GetAcceleratorProcessingRestriction(int action) {
1297 ash::Shell* shell = ash::Shell::GetInstance();
1298 if (!shell->session_state_delegate()->IsActiveUserSessionStarted() &&
1299 actions_allowed_at_login_screen_.find(action) ==
1300 actions_allowed_at_login_screen_.end()) {
1301 return RESTRICTION_PREVENT_PROCESSING;
1303 if (shell->session_state_delegate()->IsScreenLocked() &&
1304 actions_allowed_at_lock_screen_.find(action) ==
1305 actions_allowed_at_lock_screen_.end()) {
1306 return RESTRICTION_PREVENT_PROCESSING;
1308 if (shell->delegate()->IsRunningInForcedAppMode() &&
1309 actions_allowed_in_app_mode_.find(action) ==
1310 actions_allowed_in_app_mode_.end()) {
1311 return RESTRICTION_PREVENT_PROCESSING;
1313 if (shell->IsSystemModalWindowOpen() &&
1314 actions_allowed_at_modal_window_.find(action) ==
1315 actions_allowed_at_modal_window_.end()) {
1316 // Note we prevent the shortcut from propagating so it will not
1317 // be passed to the modal window. This is important for things like
1318 // Alt+Tab that would cause an undesired effect in the modal window by
1319 // cycling through its window elements.
1320 return RESTRICTION_PREVENT_PROCESSING_AND_PROPAGATION;
1322 if (shell->mru_window_tracker()->BuildMruWindowList().empty() &&
1323 actions_needing_window_.find(action) != actions_needing_window_.end()) {
1324 Shell::GetInstance()->accessibility_delegate()->TriggerAccessibilityAlert(
1325 ui::A11Y_ALERT_WINDOW_NEEDED);
1326 return RESTRICTION_PREVENT_PROCESSING_AND_PROPAGATION;
1328 return RESTRICTION_NONE;
1331 void AcceleratorController::SetKeyboardBrightnessControlDelegate(
1332 scoped_ptr<KeyboardBrightnessControlDelegate>
1333 keyboard_brightness_control_delegate) {
1334 keyboard_brightness_control_delegate_ =
1335 keyboard_brightness_control_delegate.Pass();
1338 } // namespace ash