Home | History | Annotate | Download | only in keyboard
      1 // Copyright (c) 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.
      4 
      5 #include "ui/keyboard/keyboard_util.h"
      6 
      7 #include <string>
      8 
      9 #include "base/command_line.h"
     10 #include "base/logging.h"
     11 #include "base/strings/string16.h"
     12 #include "grit/keyboard_resources.h"
     13 #include "grit/keyboard_resources_map.h"
     14 #include "ui/aura/client/aura_constants.h"
     15 #include "ui/aura/root_window.h"
     16 #include "ui/base/ime/input_method.h"
     17 #include "ui/base/ime/text_input_client.h"
     18 #include "ui/keyboard/keyboard_switches.h"
     19 
     20 namespace keyboard {
     21 
     22 bool IsKeyboardEnabled() {
     23   return CommandLine::ForCurrentProcess()->HasSwitch(
     24       switches::kEnableVirtualKeyboard);
     25 }
     26 
     27 bool InsertText(const base::string16& text, aura::RootWindow* root_window) {
     28   if (!root_window)
     29     return false;
     30 
     31   // Handle Backspace and Enter specially: using TextInputClient::InsertText is
     32   // very unreliable for these characters.
     33   // TODO(bryeung): remove this code once virtual keyboards are able to send
     34   // these events directly via the Input Injection API.
     35   if (text.length() == 1) {
     36     ui::KeyboardCode code = ui::VKEY_UNKNOWN;
     37     if (text[0] == L'\n')
     38       code = ui::VKEY_RETURN;
     39     else if (text[0] == L'\b')
     40       code = ui::VKEY_BACK;
     41 
     42     if (code != ui::VKEY_UNKNOWN) {
     43       ui::KeyEvent press_event(ui::ET_KEY_PRESSED, code, 0, 0);
     44       root_window->AsRootWindowHostDelegate()->OnHostKeyEvent(&press_event);
     45 
     46       ui::KeyEvent release_event(ui::ET_KEY_RELEASED, code, 0, 0);
     47       root_window->AsRootWindowHostDelegate()->OnHostKeyEvent(&release_event);
     48 
     49       return true;
     50     }
     51   }
     52 
     53   ui::InputMethod* input_method = root_window->GetProperty(
     54       aura::client::kRootWindowInputMethodKey);
     55   if (!input_method)
     56     return false;
     57 
     58   ui::TextInputClient* tic = input_method->GetTextInputClient();
     59   if (!tic || tic->GetTextInputType() == ui::TEXT_INPUT_TYPE_NONE)
     60     return false;
     61 
     62   tic->InsertText(text);
     63 
     64   return true;
     65 }
     66 
     67 // TODO(varunjain): It would be cleaner to have something in the
     68 // ui::TextInputClient interface, say MoveCaretInDirection(). The code in
     69 // here would get the ui::InputMethod from the root_window, and the
     70 // ui::TextInputClient from that (see above in InsertText()).
     71 bool MoveCursor(int swipe_direction,
     72                 int modifier_flags,
     73                 aura::RootWindow* root_window) {
     74   if (!root_window)
     75     return false;
     76   ui::KeyboardCode codex = ui::VKEY_UNKNOWN;
     77   ui::KeyboardCode codey = ui::VKEY_UNKNOWN;
     78   if (swipe_direction & kCursorMoveRight)
     79     codex = ui::VKEY_RIGHT;
     80   else if (swipe_direction & kCursorMoveLeft)
     81     codex = ui::VKEY_LEFT;
     82 
     83   if (swipe_direction & kCursorMoveUp)
     84     codey = ui::VKEY_UP;
     85   else if (swipe_direction & kCursorMoveDown)
     86     codey = ui::VKEY_DOWN;
     87 
     88   // First deal with the x movement.
     89   if (codex != ui::VKEY_UNKNOWN) {
     90     ui::KeyEvent press_event(ui::ET_KEY_PRESSED, codex, modifier_flags, 0);
     91     root_window->AsRootWindowHostDelegate()->OnHostKeyEvent(&press_event);
     92     ui::KeyEvent release_event(ui::ET_KEY_RELEASED, codex, modifier_flags, 0);
     93     root_window->AsRootWindowHostDelegate()->OnHostKeyEvent(&release_event);
     94   }
     95 
     96   // Then deal with the y movement.
     97   if (codey != ui::VKEY_UNKNOWN) {
     98     ui::KeyEvent press_event(ui::ET_KEY_PRESSED, codey, modifier_flags, 0);
     99     root_window->AsRootWindowHostDelegate()->OnHostKeyEvent(&press_event);
    100     ui::KeyEvent release_event(ui::ET_KEY_RELEASED, codey, modifier_flags, 0);
    101     root_window->AsRootWindowHostDelegate()->OnHostKeyEvent(&release_event);
    102   }
    103   return true;
    104 }
    105 
    106 const GritResourceMap* GetKeyboardExtensionResources(size_t* size) {
    107   // This looks a lot like the contents of a resource map; however it is
    108   // necessary to have a custom path for the extension path, so the resource
    109   // map cannot be used directly.
    110   static const GritResourceMap kKeyboardResources[] = {
    111     {"keyboard/api_adapter.js", IDR_KEYBOARD_API_ADAPTER_JS},
    112     {"keyboard/constants.js", IDR_KEYBOARD_CONSTANTS_JS},
    113     {"keyboard/elements/kb-altkey.html", IDR_KEYBOARD_ELEMENTS_ALTKEY},
    114     {"keyboard/elements/kb-altkey-container.html",
    115         IDR_KEYBOARD_ELEMENTS_ALTKEY_CONTAINER},
    116     {"keyboard/elements/kb-altkey-data.html",
    117         IDR_KEYBOARD_ELEMENTS_ALTKEY_DATA},
    118     {"keyboard/elements/kb-altkey-set.html", IDR_KEYBOARD_ELEMENTS_ALTKEY_SET},
    119     {"keyboard/elements/kb-key.html", IDR_KEYBOARD_ELEMENTS_KEY},
    120     {"keyboard/elements/kb-key-base.html", IDR_KEYBOARD_ELEMENTS_KEY_BASE},
    121     {"keyboard/elements/kb-key-import.html",
    122         IDR_KEYBOARD_ELEMENTS_KEY_IMPORT},
    123     {"keyboard/elements/kb-key-sequence.html",
    124         IDR_KEYBOARD_ELEMENTS_KEY_SEQUENCE},
    125     {"keyboard/elements/kb-keyboard.html", IDR_KEYBOARD_ELEMENTS_KEYBOARD},
    126     {"keyboard/elements/kb-keyset.html", IDR_KEYBOARD_ELEMENTS_KEYSET},
    127     {"keyboard/elements/kb-row.html", IDR_KEYBOARD_ELEMENTS_ROW},
    128     {"keyboard/images/keyboard.svg", IDR_KEYBOARD_IMAGES_KEYBOARD},
    129     {"keyboard/images/microphone.svg", IDR_KEYBOARD_IMAGES_MICROPHONE},
    130     {"keyboard/images/microphone-green.svg",
    131         IDR_KEYBOARD_IMAGES_MICROPHONE_GREEN},
    132     {"keyboard/index.html", IDR_KEYBOARD_INDEX},
    133     {"keyboard/layouts/dvorak.html", IDR_KEYBOARD_LAYOUTS_DVORAK},
    134     {"keyboard/layouts/latin-accents.js", IDR_KEYBOARD_LAYOUTS_LATIN_ACCENTS},
    135     {"keyboard/layouts/qwerty.html", IDR_KEYBOARD_LAYOUTS_QWERTY},
    136     {"keyboard/layouts/symbol-altkeys.js",
    137         IDR_KEYBOARD_LAYOUTS_SYMBOL_ALTKEYS},
    138     {"keyboard/layouts/spacebar-row.html", IDR_KEYBOARD_SPACEBAR_ROW},
    139     {"keyboard/main.js", IDR_KEYBOARD_MAIN_JS},
    140     {"keyboard/manifest.json", IDR_KEYBOARD_MANIFEST},
    141     {"keyboard/main.css", IDR_KEYBOARD_MAIN_CSS},
    142     {"keyboard/polymer.min.js", IDR_KEYBOARD_POLYMER},
    143     {"keyboard/voice_input.js", IDR_KEYBOARD_VOICE_INPUT_JS},
    144   };
    145   static const size_t kKeyboardResourcesSize = arraysize(kKeyboardResources);
    146   *size = kKeyboardResourcesSize;
    147   return kKeyboardResources;
    148 }
    149 
    150 }  // namespace keyboard
    151