1eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch// Copyright 2013 The Chromium Authors. All rights reserved.
2eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch// Use of this source code is governed by a BSD-style license that can be
3eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch// found in the LICENSE file.
4eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
55d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "chrome/browser/chromeos/events/keyboard_driven_event_rewriter.h"
6eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
7116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch#include "chrome/browser/chromeos/events/event_rewriter.h"
8558790d6acca3451cf3a6b497803a5f07d0bec58Ben Murdoch#include "chrome/browser/chromeos/system/input_device_settings.h"
96e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)#include "components/user_manager/user_manager.h"
105c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu#include "ui/events/event.h"
115d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "ui/events/event_utils.h"
12eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
13eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdochnamespace chromeos {
14eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
15eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdochnamespace {
16eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
17a3f7b4e666c476898878fa745f637129375cd889Ben Murdochconst int kModifierMask = ui::EF_SHIFT_DOWN;
18eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
19eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch// Returns true if and only if it is on login screen (i.e. user is not logged
20eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch// in) and the keyboard driven flag in the OEM manifest is on.
21eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdochbool ShouldStripModifiersForArrowKeysAndEnter() {
226e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)  if (user_manager::UserManager::IsInitialized() &&
236e8cce623b6e4fe0c9e4af605d675dd9d0338c38Torne (Richard Coles)      !user_manager::UserManager::Get()->IsSessionStarted()) {
245d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)    return system::InputDeviceSettings::Get()
255d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)        ->ForceKeyboardDrivenUINavigation();
26eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  }
27eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
28eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  return false;
29eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch}
30eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
31eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch}  // namespace
32eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
33eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen MurdochKeyboardDrivenEventRewriter::KeyboardDrivenEventRewriter() {}
34eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
35eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen MurdochKeyboardDrivenEventRewriter::~KeyboardDrivenEventRewriter() {}
36eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
375c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liuui::EventRewriteStatus KeyboardDrivenEventRewriter::RewriteForTesting(
385c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    const ui::Event& event,
395c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    scoped_ptr<ui::Event>* rewritten_event) {
405c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  return Rewrite(event, rewritten_event);
415c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu}
425c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu
435c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liuui::EventRewriteStatus KeyboardDrivenEventRewriter::RewriteEvent(
445c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    const ui::Event& event,
455c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    scoped_ptr<ui::Event>* rewritten_event) {
46eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  if (!ShouldStripModifiersForArrowKeysAndEnter())
475c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    return ui::EVENT_REWRITE_CONTINUE;
48eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
495c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  return Rewrite(event, rewritten_event);
50eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch}
51eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
525c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liuui::EventRewriteStatus KeyboardDrivenEventRewriter::NextDispatchEvent(
535c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    const ui::Event& last_event,
545c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    scoped_ptr<ui::Event>* new_event) {
555c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  NOTREACHED();
565c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  return ui::EVENT_REWRITE_CONTINUE;
57eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch}
58eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
595c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liuui::EventRewriteStatus KeyboardDrivenEventRewriter::Rewrite(
605c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    const ui::Event& event,
615c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    scoped_ptr<ui::Event>* rewritten_event) {
625c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  int flags = event.flags();
635d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  if ((flags & kModifierMask) != kModifierMask)
645c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    return ui::EVENT_REWRITE_CONTINUE;
655c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu
665c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  DCHECK(event.type() == ui::ET_KEY_PRESSED ||
675c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu         event.type() == ui::ET_KEY_RELEASED)
685c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      << "Unexpected event type " << event.type();
695c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  const ui::KeyEvent& key_event = static_cast<const ui::KeyEvent&>(event);
705c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  ui::KeyboardCode key_code = key_event.key_code();
715d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
725d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)  if (key_code != ui::VKEY_LEFT &&
735d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      key_code != ui::VKEY_RIGHT &&
745d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      key_code != ui::VKEY_UP &&
755d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      key_code != ui::VKEY_DOWN &&
765d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      key_code != ui::VKEY_RETURN &&
775d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)      key_code != ui::VKEY_F6) {
785c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    return ui::EVENT_REWRITE_CONTINUE;
79eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch  }
80eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
81116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch  chromeos::EventRewriter::BuildRewrittenKeyEvent(
82116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch      key_event,
83116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch      key_event.key_code(),
84116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch      flags & ~(ui::EF_CONTROL_DOWN | ui::EF_ALT_DOWN | ui::EF_SHIFT_DOWN),
85116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch      rewritten_event);
865c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  return ui::EVENT_REWRITE_REWRITTEN;
87eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch}
88eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch
89eb525c5499e34cc9c4b825d6d9e75bb07cc06aceBen Murdoch}  // namespace chromeos
90