• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1<!--
2  -- Copyright 2013 The Chromium Authors. All rights reserved.
3  -- Use of this source code is governed by a BSD-style license that can be
4  -- found in the LICENSE file.
5  -->
6
7<polymer-element name="kb-key-codes">
8<script>
9  (function() {
10
11    // Flag values for ctrl, alt and shift as defined by EventFlags
12    // in "event_constants.h".
13    // @enum {number}
14    var Modifier = {
15      NONE: 0,
16      ALT: 8,
17      CONTROL: 4,
18      SHIFT: 2
19    }
20
21    // Each virtual key event is assigned a unique ID.
22    var nextRequestID = 0;
23
24    // Keycodes have been deprecated in the KeyEvent specification, but are
25    // nonetheless required to support legacy web content.  The Keycodes in the
26    // following table are based on subset of US-EN 101-key keyboard. These
27    // codes are used in the absence of explicit keycodes for kb-key and
28    // kb-keysequence elements. Keyboard layout authors may explicitly set the
29    // keyCode attribute for kb-key or kb-keysequence elements to refer to
30    // indices in this table in order to emulate a physical keyboard with an
31    // alternate layout.  Not all keys on a virtual keyboard are required to
32    // have keyCodes. The shiftModifier specifies whether to always include or
33    // exclude the shift modifer when sending key events for this key. If it's
34    // undefined, it will defer to state of the keyboard.
35    // TODO(rsadam): Correctly propagate shutdown keycode. This is currently
36    // ignored due to chromoting (crbug/146609)
37    var keyCodes = {
38      '\b': {keyCode: 0x08, keyName: 'Backspace', shiftModifier: false},
39      '\t': {keyCode: 0x09, keyName: 'Tab', shiftModifier: false},
40      '\n': {keyCode: 0x0D, keyName: 'Enter', shiftModifier: false},
41      'Esc': {keyCode: 0x1B, keyName: 'Escape', shiftModifier: false},
42      ' ': {keyCode: 0x20, keyName: 'Space', shiftModifier: false},
43      'Arrow-Left': {keyCode: 0x25, keyName: 'ArrowLeft',
44          shiftModifier: undefined},
45      'Arrow-Up': {keyCode: 0x26, keyName: 'ArrowUp', shiftModifier: undefined},
46      'Arrow-Right': {keyCode: 0x27, keyName: 'ArrowRight',
47          shiftModifier: undefined},
48      'Arrow-Down': {keyCode: 0x28, keyName: 'ArrowDown',
49          shiftModifier: undefined},
50      '0': {keyCode: 0x30, keyName: 'Digit0', shiftModifier: false},
51      ')': {keyCode: 0x30, keyName: 'Digit0', shiftModifier: true},
52      '1': {keyCode: 0x31, keyName: 'Digit1', shiftModifier: false},
53      '!': {keyCode: 0x31, keyName: 'Digit1', shiftModifier: true},
54      '2': {keyCode: 0x32, keyName: 'Digit2', shiftModifier: false},
55      '@': {keyCode: 0x32, keyName: 'Digit2', shiftModifier: true},
56      '3': {keyCode: 0x33, keyName: 'Digit3', shiftModifier: false},
57      '#': {keyCode: 0x33, keyName: 'Digit3', shiftModifier: true},
58      '4': {keyCode: 0x34, keyName: 'Digit4', shiftModifier: false},
59      '$': {keyCode: 0x34, keyName: 'Digit4', shiftModifier: true},
60      '5': {keyCode: 0x35, keyName: 'Digit5', shiftModifier: false},
61      '%': {keyCode: 0x35, keyName: 'Digit5', shiftModifier: true},
62      '6': {keyCode: 0x36, keyName: 'Digit6', shiftModifier: false},
63      '^': {keyCode: 0x36, keyName: 'Digit6', shiftModifier: true},
64      '7': {keyCode: 0x37, keyName: 'Digit7', shiftModifier: false},
65      '&': {keyCode: 0x37, keyName: 'Digit7', shiftModifier: true},
66      '8': {keyCode: 0x38, keyName: 'Digit8', shiftModifier: false},
67      '*': {keyCode: 0x38, keyName: 'Digit8', shiftModifier: true},
68      '9': {keyCode: 0x39, keyName: 'Digit9', shiftModifier: false},
69      '(': {keyCode: 0x39, keyName: 'Digit9', shiftModifier: true},
70      'a': {keyCode: 0x41, keyName: 'KeyA', shiftModifier: false},
71      'A': {keyCode: 0x41, keyName: 'KeyA', shiftModifier: true},
72      'b': {keyCode: 0x42, keyName: 'KeyB', shiftModifier: false},
73      'B': {keyCode: 0x42, keyName: 'KeyB', shiftModifier: true},
74      'c': {keyCode: 0x43, keyName: 'KeyC', shiftModifier: false},
75      'C': {keyCode: 0x43, keyName: 'KeyC', shiftModifier: true},
76      'd': {keyCode: 0x44, keyName: 'KeyD', shiftModifier: false},
77      'D': {keyCode: 0x44, keyName: 'KeyD', shiftModifier: true},
78      'e': {keyCode: 0x45, keyName: 'KeyE', shiftModifier: false},
79      'E': {keyCode: 0x45, keyName: 'KeyE', shiftModifier: true},
80      'f': {keyCode: 0x46, keyName: 'KeyF', shiftModifier: false},
81      'F': {keyCode: 0x46, keyName: 'KeyF', shiftModifier: true},
82      'g': {keyCode: 0x47, keyName: 'KeyG', shiftModifier: false},
83      'G': {keyCode: 0x47, keyName: 'KeyG', shiftModifier: true},
84      'h': {keyCode: 0x48, keyName: 'KeyH', shiftModifier: false},
85      'H': {keyCode: 0x48, keyName: 'KeyH', shiftModifier: true},
86      'i': {keyCode: 0x49, keyName: 'KeyI', shiftModifier: false},
87      'I': {keyCode: 0x49, keyName: 'KeyI', shiftModifier: true},
88      'j': {keyCode: 0x4A, keyName: 'KeyJ', shiftModifier: false},
89      'J': {keyCode: 0x4A, keyName: 'KeyJ', shiftModifier: true},
90      'k': {keyCode: 0x4B, keyName: 'KeyK', shiftModifier: false},
91      'K': {keyCode: 0x4B, keyName: 'KeyK', shiftModifier: true},
92      'l': {keyCode: 0x4C, keyName: 'KeyL', shiftModifier: false},
93      'L': {keyCode: 0x4C, keyName: 'KeyL', shiftModifier: true},
94      'm': {keyCode: 0x4D, keyName: 'KeyM', shiftModifier: false},
95      'M': {keyCode: 0x4D, keyName: 'KeyM', shiftModifier: true},
96      'n': {keyCode: 0x4E, keyName: 'KeyN', shiftModifier: false},
97      'N': {keyCode: 0x4E, keyName: 'KeyN', shiftModifier: true},
98      'o': {keyCode: 0x4F, keyName: 'KeyO', shiftModifier: false},
99      'O': {keyCode: 0x4F, keyName: 'KeyO', shiftModifier: true},
100      'p': {keyCode: 0x50, keyName: 'KeyP', shiftModifier: false},
101      'P': {keyCode: 0x50, keyName: 'KeyP', shiftModifier: true},
102      'q': {keyCode: 0x51, keyName: 'KeyQ', shiftModifier: false},
103      'Q': {keyCode: 0x51, keyName: 'KeyQ', shiftModifier: true},
104      'r': {keyCode: 0x52, keyName: 'KeyR', shiftModifier: false},
105      'R': {keyCode: 0x52, keyName: 'KeyR', shiftModifier: true},
106      's': {keyCode: 0x53, keyName: 'KeyS', shiftModifier: false},
107      'S': {keyCode: 0x53, keyName: 'KeyS', shiftModifier: true},
108      't': {keyCode: 0x54, keyName: 'KeyT', shiftModifier: false},
109      'T': {keyCode: 0x54, keyName: 'KeyT', shiftModifier: true},
110      'u': {keyCode: 0x55, keyName: 'KeyU', shiftModifier: false},
111      'U': {keyCode: 0x55, keyName: 'KeyU', shiftModifier: true},
112      'v': {keyCode: 0x56, keyName: 'KeyV', shiftModifier: false},
113      'V': {keyCode: 0x56, keyName: 'KeyV', shiftModifier: true},
114      'w': {keyCode: 0x57, keyName: 'KeyW', shiftModifier: false},
115      'W': {keyCode: 0x57, keyName: 'KeyW', shiftModifier: true},
116      'x': {keyCode: 0x58, keyName: 'KeyX', shiftModifier: false},
117      'X': {keyCode: 0x58, keyName: 'KeyX', shiftModifier: true},
118      'y': {keyCode: 0x59, keyName: 'KeyY', shiftModifier: false},
119      'Y': {keyCode: 0x59, keyName: 'KeyY', shiftModifier: true},
120      'z': {keyCode: 0x5A, keyName: 'KeyZ', shiftModifier: false},
121      'Z': {keyCode: 0x5A, keyName: 'KeyZ', shiftModifier: true},
122      'Fullscreen': {keyCode: 0x7A, shiftModifier: false},
123      'Shutdown': {keyCode: 0x98, shiftModifier: false},
124      'Back': {keyCode: 0xA6, shiftModifier: false},
125      'Forward': {keyCode: 0xA7, shiftModifier: false},
126      'Reload': {keyCode: 0xA8, shiftModifier: false},
127      'Search': {keyCode: 0xAA, shiftModifier: false},
128      'Mute': {keyCode: 0xAD, keyName: 'VolumeMute', shiftModifier: false},
129      'Volume-Down': {keyCode: 0xAE, keyName: 'VolumeDown',
130          shiftModifier: false},
131      'Volume-Up': {keyCode: 0xAF, keyName: 'VolumeUp', shiftModifier: false},
132      'Change-Window': {keyCode: 0xB6, shiftModifier: false},
133      ';': {keyCode: 0xBA, keyName: 'Semicolon', shiftModifier: false},
134      ':': {keyCode: 0xBA, keyName: 'Semicolon',shiftModifier: true},
135      '=': {keyCode: 0xBB, keyName: 'Equal', shiftModifier: false},
136      '+': {keyCode: 0xBB, keyName: 'Equal', shiftModifier: true},
137      ',': {keyCode: 0xBC, keyName: 'Comma', shiftModifier: false},
138      '<': {keyCode: 0xBC, keyName: 'Comma', shiftModifier: true},
139      '-': {keyCode: 0xBD, keyName: 'Minus', shiftModifier: false},
140      '_': {keyCode: 0xBD, keyName: 'Minus', shiftModifier: true},
141      '.': {keyCode: 0xBE, keyName: 'Period', shiftModifier: false},
142      '>': {keyCode: 0xBE, keyName: 'Period', shiftModifier: true},
143      '/': {keyCode: 0xBF, keyName: 'Slash', shiftModifier: false},
144      '?': {keyCode: 0xBF, keyName: 'Slash', shiftModifier: true},
145      '`': {keyCode: 0xC0, keyName: 'Backquote', shiftModifier: false},
146      '~': {keyCode: 0xC0, keyName: 'Backquote', shiftModifier: true},
147      'Brightness-Down': {keyCode: 0xD8, keyName: 'BrightnessDown',
148          shiftModifier: false},
149      'Brightness-Up': {keyCode: 0xD9, keyName: 'BrightnessUp',
150          shiftModifier: false},
151      '[': {keyCode: 0xDB, keyName: 'BracketLeft', shiftModifier: false},
152      '{': {keyCode: 0xDB, keyName: 'BracketLeft', shiftModifier: true},
153      '\\': {keyCode: 0xDC, keyName: 'Backslash', shiftModifier: false},
154      '|': {keyCode: 0xDC, keyName: 'Backslash', shiftModifier: true},
155      ']': {keyCode: 0xDD, keyName: 'BracketRight', shiftModifier: false},
156      '}': {keyCode: 0xDD, keyName: 'BracketRight', shiftModifier: true},
157      '\'': {keyCode: 0xDE, keyName: 'Quote', shiftModifier: false},
158      '"': {keyCode: 0xDE, keyName: 'Quote', shiftModifier: true},
159    };
160
161    Polymer('kb-key-codes', {
162      /**
163       * Retrieves the keyCode and status of the shift modifier.
164       * @param {string} id ID of an entry in the code table.
165       * @return {keyCode: numeric, shiftModifier: boolean}
166       */
167      GetKeyCodeAndModifiers: function(id) {
168        var entry = keyCodes[id];
169        if (entry) {
170          return {
171            keyCode: entry.keyCode,
172            keyName: entry.keyName || 'Unidentified',
173            shiftModifier: entry.shiftModifier
174          };
175        }
176        if (id.length != 1)
177          return;
178        // Special case of accented characters.
179        return {
180          keyCode: 0,
181          keyName: 'Unidentified',
182          shiftModifier: false
183        };
184      },
185
186     /**
187      * Creates a virtual key event for use with the keyboard extension API.
188      * See http://www.w3.org/TR/DOM-Level-3-Events/#events-KeyboardEvent.
189      * @param {Object} detail Attribute of the key being pressed or released.
190      * @param {string} type The type of key event, which may be keydown
191      *     or keyup.
192      * @return {?KeyboardEvent} A KeyboardEvent object, or undefined on
193      *     failure.
194      */
195     createVirtualKeyEvent: function(detail, type) {
196       var char = detail.char;
197       var keyCode = detail.keyCode;
198       var keyName = detail.keyName;
199       // The shift modifier is handled specially. Some charactares like '+'
200       // {keyCode: 0xBB, shiftModifier: true}, are available on non-upper
201       // keysets, and so we rely on caching the correct shiftModifier. If
202       // the cached value of the shiftModifier is undefined, we defer to
203       // the shiftModifier in the detail.
204       var shiftModifier = detail.shiftModifier;
205       if (keyCode == undefined || keyName == undefined) {
206         var state = this.GetKeyCodeAndModifiers(char);
207         if (state) {
208           keyCode = keyCode || state.keyCode;
209           keyName = keyName || state.keyName;
210           shiftModifier = (state.shiftModifier == undefined) ?
211               shiftModifier : state.shiftModifier;
212         } else {
213           // Keycode not defined.
214           return;
215         }
216       }
217       var modifiers = Modifier.NONE;
218       modifiers = shiftModifier ? modifiers | Modifier.SHIFT : modifiers;
219       modifiers = detail.controlModifier ?
220           modifiers | Modifier.CONTROL : modifiers;
221       modifiers = detail.altModifier ? modifiers | Modifier.ALT : modifiers;
222       return {
223         type: type,
224         charValue: char.charCodeAt(0),
225         keyCode: keyCode,
226         keyName: keyName,
227         modifiers: modifiers
228       };
229     },
230    });
231  })();
232</script>
233</polymer-element>
234