diff options
27 files changed, 2901 insertions, 203 deletions
diff --git a/api/current.xml b/api/current.xml index b51242b..1f3a6b7 100644 --- a/api/current.xml +++ b/api/current.xml @@ -195848,6 +195848,17 @@ <parameter name="keyCode" type="int"> </parameter> </method> +<method name="isNumLockLatched" + return="boolean" + abstract="false" + native="false" + synchronized="false" + static="false" + final="true" + deprecated="not deprecated" + visibility="public" +> +</method> <method name="isPrintingKey" return="boolean" abstract="false" @@ -196530,6 +196541,39 @@ visibility="public" > </method> +<method name="isCapsLockLatched" + return="boolean" + abstract="false" + native="false" + synchronized="false" + static="false" + final="true" + deprecated="not deprecated" + visibility="public" +> +</method> +<method name="isCtrlPressed" + return="boolean" + abstract="false" + native="false" + synchronized="false" + static="false" + final="true" + deprecated="not deprecated" + visibility="public" +> +</method> +<method name="isFunctionPressed" + return="boolean" + abstract="false" + native="false" + synchronized="false" + static="false" + final="true" + deprecated="not deprecated" + visibility="public" +> +</method> <method name="isLongPress" return="boolean" abstract="false" @@ -196541,6 +196585,17 @@ visibility="public" > </method> +<method name="isMetaPressed" + return="boolean" + abstract="false" + native="false" + synchronized="false" + static="false" + final="true" + deprecated="not deprecated" + visibility="public" +> +</method> <method name="isModifierKey" return="boolean" abstract="false" @@ -196565,6 +196620,17 @@ visibility="public" > </method> +<method name="isScrollLockLatched" + return="boolean" + abstract="false" + native="false" + synchronized="false" + static="false" + final="true" + deprecated="not deprecated" + visibility="public" +> +</method> <method name="isShiftPressed" return="boolean" abstract="false" @@ -196986,6 +197052,17 @@ visibility="public" > </field> +<field name="KEYCODE_BREAK" + type="int" + transient="false" + volatile="false" + value="121" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_BUTTON_A" type="int" transient="false" @@ -197184,6 +197261,17 @@ visibility="public" > </field> +<field name="KEYCODE_CAPS_LOCK" + type="int" + transient="false" + volatile="false" + value="115" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_CLEAR" type="int" transient="false" @@ -197206,6 +197294,28 @@ visibility="public" > </field> +<field name="KEYCODE_CTRL_LEFT" + type="int" + transient="false" + volatile="false" + value="113" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_CTRL_RIGHT" + type="int" + transient="false" + volatile="false" + value="114" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_D" type="int" transient="false" @@ -197338,6 +197448,17 @@ visibility="public" > </field> +<field name="KEYCODE_ESCAPE" + type="int" + transient="false" + volatile="false" + value="111" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_EXPLORER" type="int" transient="false" @@ -197360,6 +197481,138 @@ visibility="public" > </field> +<field name="KEYCODE_F1" + type="int" + transient="false" + volatile="false" + value="131" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_F10" + type="int" + transient="false" + volatile="false" + value="140" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_F11" + type="int" + transient="false" + volatile="false" + value="141" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_F12" + type="int" + transient="false" + volatile="false" + value="142" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_F2" + type="int" + transient="false" + volatile="false" + value="132" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_F3" + type="int" + transient="false" + volatile="false" + value="133" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_F4" + type="int" + transient="false" + volatile="false" + value="134" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_F5" + type="int" + transient="false" + volatile="false" + value="135" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_F6" + type="int" + transient="false" + volatile="false" + value="136" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_F7" + type="int" + transient="false" + volatile="false" + value="137" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_F8" + type="int" + transient="false" + volatile="false" + value="138" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_F9" + type="int" + transient="false" + volatile="false" + value="139" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_FOCUS" type="int" transient="false" @@ -197371,6 +197624,39 @@ visibility="public" > </field> +<field name="KEYCODE_FORWARD" + type="int" + transient="false" + volatile="false" + value="125" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_FORWARD_DEL" + type="int" + transient="false" + volatile="false" + value="112" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_FUNCTION" + type="int" + transient="false" + volatile="false" + value="119" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_G" type="int" transient="false" @@ -197437,6 +197723,17 @@ visibility="public" > </field> +<field name="KEYCODE_INSERT" + type="int" + transient="false" + volatile="false" + value="124" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_J" type="int" transient="false" @@ -197492,6 +197789,28 @@ visibility="public" > </field> +<field name="KEYCODE_MEDIA_CLOSE" + type="int" + transient="false" + volatile="false" + value="128" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_MEDIA_EJECT" + type="int" + transient="false" + volatile="false" + value="129" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_MEDIA_FAST_FORWARD" type="int" transient="false" @@ -197514,6 +197833,28 @@ visibility="public" > </field> +<field name="KEYCODE_MEDIA_PAUSE" + type="int" + transient="false" + volatile="false" + value="127" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_MEDIA_PLAY" + type="int" + transient="false" + volatile="false" + value="126" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_MEDIA_PLAY_PAUSE" type="int" transient="false" @@ -197536,6 +197877,17 @@ visibility="public" > </field> +<field name="KEYCODE_MEDIA_RECORD" + type="int" + transient="false" + volatile="false" + value="130" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_MEDIA_REWIND" type="int" transient="false" @@ -197569,6 +197921,28 @@ visibility="public" > </field> +<field name="KEYCODE_META_LEFT" + type="int" + transient="false" + volatile="false" + value="117" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_META_RIGHT" + type="int" + transient="false" + volatile="false" + value="118" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_MINUS" type="int" transient="false" @@ -197580,6 +197954,28 @@ visibility="public" > </field> +<field name="KEYCODE_MOVE_END" + type="int" + transient="false" + volatile="false" + value="123" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_MOVE_HOME" + type="int" + transient="false" + volatile="false" + value="122" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_MUTE" type="int" transient="false" @@ -197624,6 +198020,237 @@ visibility="public" > </field> +<field name="KEYCODE_NUMPAD_0" + type="int" + transient="false" + volatile="false" + value="144" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_1" + type="int" + transient="false" + volatile="false" + value="145" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_2" + type="int" + transient="false" + volatile="false" + value="146" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_3" + type="int" + transient="false" + volatile="false" + value="147" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_4" + type="int" + transient="false" + volatile="false" + value="148" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_5" + type="int" + transient="false" + volatile="false" + value="149" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_6" + type="int" + transient="false" + volatile="false" + value="150" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_7" + type="int" + transient="false" + volatile="false" + value="151" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_8" + type="int" + transient="false" + volatile="false" + value="152" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_9" + type="int" + transient="false" + volatile="false" + value="153" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_ADD" + type="int" + transient="false" + volatile="false" + value="157" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_COMMA" + type="int" + transient="false" + volatile="false" + value="159" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_DIVIDE" + type="int" + transient="false" + volatile="false" + value="154" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_DOT" + type="int" + transient="false" + volatile="false" + value="158" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_ENTER" + type="int" + transient="false" + volatile="false" + value="160" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_EQUALS" + type="int" + transient="false" + volatile="false" + value="161" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_LEFT_PAREN" + type="int" + transient="false" + volatile="false" + value="162" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_MULTIPLY" + type="int" + transient="false" + volatile="false" + value="155" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_RIGHT_PAREN" + type="int" + transient="false" + volatile="false" + value="163" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUMPAD_SUBTRACT" + type="int" + transient="false" + volatile="false" + value="156" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="KEYCODE_NUM_LOCK" + type="int" + transient="false" + volatile="false" + value="143" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_O" type="int" transient="false" @@ -197767,6 +198394,17 @@ visibility="public" > </field> +<field name="KEYCODE_SCROLL_LOCK" + type="int" + transient="false" + volatile="false" + value="116" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_SEARCH" type="int" transient="false" @@ -197888,6 +198526,17 @@ visibility="public" > </field> +<field name="KEYCODE_SYSRQ" + type="int" + transient="false" + volatile="false" + value="120" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="KEYCODE_T" type="int" transient="false" @@ -198053,6 +198702,116 @@ visibility="public" > </field> +<field name="META_CAPS_LOCK_LATCHED" + type="int" + transient="false" + volatile="false" + value="1048576" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="META_CTRL_LEFT_ON" + type="int" + transient="false" + volatile="false" + value="8192" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="META_CTRL_ON" + type="int" + transient="false" + volatile="false" + value="4096" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="META_CTRL_RIGHT_ON" + type="int" + transient="false" + volatile="false" + value="16384" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="META_FUNCTION_ON" + type="int" + transient="false" + volatile="false" + value="8" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="META_META_LEFT_ON" + type="int" + transient="false" + volatile="false" + value="131072" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="META_META_ON" + type="int" + transient="false" + volatile="false" + value="65536" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="META_META_RIGHT_ON" + type="int" + transient="false" + volatile="false" + value="262144" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="META_NUM_LOCK_LATCHED" + type="int" + transient="false" + volatile="false" + value="2097152" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> +<field name="META_SCROLL_LOCK_LATCHED" + type="int" + transient="false" + volatile="false" + value="4194304" + static="true" + final="true" + deprecated="not deprecated" + visibility="public" +> +</field> <field name="META_SHIFT_LEFT_ON" type="int" transient="false" diff --git a/core/java/android/text/Layout.java b/core/java/android/text/Layout.java index 54ac906..dd25eaa 100644 --- a/core/java/android/text/Layout.java +++ b/core/java/android/text/Layout.java @@ -1145,12 +1145,9 @@ public abstract class Layout { float h2 = isLevelBoundary(point) ? getSecondaryHorizontal(point) - 0.5f : h1; - int caps = TextKeyListener.getMetaState(editingBuffer, - KeyEvent.META_SHIFT_ON) | - TextKeyListener.getMetaState(editingBuffer, - TextKeyListener.META_SELECTING); - int fn = TextKeyListener.getMetaState(editingBuffer, - KeyEvent.META_ALT_ON); + int caps = TextKeyListener.getMetaState(editingBuffer, TextKeyListener.META_SHIFT_ON) | + TextKeyListener.getMetaState(editingBuffer, TextKeyListener.META_SELECTING); + int fn = TextKeyListener.getMetaState(editingBuffer, TextKeyListener.META_ALT_ON); int dist = 0; if (caps != 0 || fn != 0) { diff --git a/core/java/android/text/method/ArrowKeyMovementMethod.java b/core/java/android/text/method/ArrowKeyMovementMethod.java index 220e023..0d012d6 100644 --- a/core/java/android/text/method/ArrowKeyMovementMethod.java +++ b/core/java/android/text/method/ArrowKeyMovementMethod.java @@ -30,12 +30,12 @@ import android.widget.TextView; public class ArrowKeyMovementMethod implements MovementMethod { private boolean isCap(Spannable buffer) { - return ((MetaKeyKeyListener.getMetaState(buffer, KeyEvent.META_SHIFT_ON) == 1) || + return ((MetaKeyKeyListener.getMetaState(buffer, MetaKeyKeyListener.META_SHIFT_ON) == 1) || (MetaKeyKeyListener.getMetaState(buffer, MetaKeyKeyListener.META_SELECTING) != 0)); } private boolean isAlt(Spannable buffer) { - return MetaKeyKeyListener.getMetaState(buffer, KeyEvent.META_ALT_ON) == 1; + return MetaKeyKeyListener.getMetaState(buffer, MetaKeyKeyListener.META_ALT_ON) == 1; } private boolean up(TextView widget, Spannable buffer) { diff --git a/core/java/android/text/method/DialerKeyListener.java b/core/java/android/text/method/DialerKeyListener.java index 584e83f..1e1812a 100644 --- a/core/java/android/text/method/DialerKeyListener.java +++ b/core/java/android/text/method/DialerKeyListener.java @@ -56,7 +56,7 @@ public class DialerKeyListener extends NumberKeyListener * Prefer number if no meta key is active, or if it produces something * valid and the meta lookup does not. */ - if ((meta & (KeyEvent.META_ALT_ON | KeyEvent.META_SHIFT_ON)) == 0) { + if ((meta & (MetaKeyKeyListener.META_ALT_ON | MetaKeyKeyListener.META_SHIFT_ON)) == 0) { if (number != 0) { return number; } diff --git a/core/java/android/text/method/MetaKeyKeyListener.java b/core/java/android/text/method/MetaKeyKeyListener.java index 61ec67f..e7b36d7 100644 --- a/core/java/android/text/method/MetaKeyKeyListener.java +++ b/core/java/android/text/method/MetaKeyKeyListener.java @@ -16,9 +16,12 @@ package android.text.method; +import android.text.Editable; +import android.text.NoCopySpan; +import android.text.Spannable; +import android.text.Spanned; import android.view.KeyEvent; import android.view.View; -import android.text.*; /** * This base class encapsulates the behavior for handling the meta keys @@ -28,38 +31,58 @@ import android.text.*; */ public abstract class MetaKeyKeyListener { + /** + * Flag that indicates that the SHIFT key is on. + * Value equals {@link KeyEvent#META_SHIFT_ON}. + */ public static final int META_SHIFT_ON = KeyEvent.META_SHIFT_ON; + /** + * Flag that indicates that the ALT key is on. + * Value equals {@link KeyEvent#META_ALT_ON}. + */ public static final int META_ALT_ON = KeyEvent.META_ALT_ON; + /** + * Flag that indicates that the SYM key is on. + * Value equals {@link KeyEvent#META_SYM_ON}. + */ public static final int META_SYM_ON = KeyEvent.META_SYM_ON; - - private static final int LOCKED_SHIFT = 8; - public static final int META_CAP_LOCKED = KeyEvent.META_SHIFT_ON << LOCKED_SHIFT; - public static final int META_ALT_LOCKED = KeyEvent.META_ALT_ON << LOCKED_SHIFT; - public static final int META_SYM_LOCKED = KeyEvent.META_SYM_ON << LOCKED_SHIFT; + /** + * Flag that indicates that the SHIFT key is locked in CAPS mode. + */ + public static final int META_CAP_LOCKED = KeyEvent.META_CAP_LOCKED; + /** + * Flag that indicates that the ALT key is locked. + */ + public static final int META_ALT_LOCKED = KeyEvent.META_ALT_LOCKED; + /** + * Flag that indicates that the SYM key is locked. + */ + public static final int META_SYM_LOCKED = KeyEvent.META_SYM_LOCKED; /** * @hide pending API review */ - public static final int META_SELECTING = 1 << 16; - - private static final int USED_SHIFT = 24; - - private static final long META_CAP_USED = ((long)KeyEvent.META_SHIFT_ON) << USED_SHIFT; - private static final long META_ALT_USED = ((long)KeyEvent.META_ALT_ON) << USED_SHIFT; - private static final long META_SYM_USED = ((long)KeyEvent.META_SYM_ON) << USED_SHIFT; - - private static final int PRESSED_SHIFT = 32; + public static final int META_SELECTING = KeyEvent.META_SELECTING; + + private static final int META_SHIFT_ON_AND_LOCKED = META_SHIFT_ON | META_CAP_LOCKED; + private static final int META_ALT_ON_AND_LOCKED = META_ALT_ON | META_ALT_LOCKED; + private static final int META_SYM_ON_AND_LOCKED = META_SYM_ON | META_SYM_LOCKED; + + // These bits are privately used by the meta key key listener. + // They are deliberately assigned values outside of the representable range of an 'int' + // so as not to conflict with any meta key states publicly defined by KeyEvent. + private static final long META_CAP_USED = 1L << 32; + private static final long META_ALT_USED = 1L << 33; + private static final long META_SYM_USED = 1L << 34; - private static final long META_CAP_PRESSED = ((long)KeyEvent.META_SHIFT_ON) << PRESSED_SHIFT; - private static final long META_ALT_PRESSED = ((long)KeyEvent.META_ALT_ON) << PRESSED_SHIFT; - private static final long META_SYM_PRESSED = ((long)KeyEvent.META_SYM_ON) << PRESSED_SHIFT; - - private static final int RELEASED_SHIFT = 40; + private static final long META_CAP_PRESSED = 1L << 40; + private static final long META_ALT_PRESSED = 1L << 41; + private static final long META_SYM_PRESSED = 1L << 42; - private static final long META_CAP_RELEASED = ((long)KeyEvent.META_SHIFT_ON) << RELEASED_SHIFT; - private static final long META_ALT_RELEASED = ((long)KeyEvent.META_ALT_ON) << RELEASED_SHIFT; - private static final long META_SYM_RELEASED = ((long)KeyEvent.META_SYM_ON) << RELEASED_SHIFT; + private static final long META_CAP_RELEASED = 1L << 48; + private static final long META_ALT_RELEASED = 1L << 49; + private static final long META_SYM_RELEASED = 1L << 50; private static final long META_SHIFT_MASK = META_SHIFT_ON | META_CAP_LOCKED | META_CAP_USED @@ -306,15 +329,14 @@ public abstract class MetaKeyKeyListener { * (arrow keys, for example) and you handle a key. */ public static long resetLockedMeta(long state) { - state = resetLock(state, META_SHIFT_ON, META_SHIFT_MASK); - state = resetLock(state, META_ALT_ON, META_ALT_MASK); - state = resetLock(state, META_SYM_ON, META_SYM_MASK); - return state; - } - - private static long resetLock(long state, int what, long mask) { - if ((state&(((long)what)<<LOCKED_SHIFT)) != 0) { - state &= ~mask; + if ((state & META_CAP_LOCKED) != 0) { + state &= ~META_SHIFT_MASK; + } + if ((state & META_ALT_LOCKED) != 0) { + state &= ~META_ALT_MASK; + } + if ((state & META_SYM_LOCKED) != 0) { + state &= ~META_SYM_MASK; } return state; } @@ -332,9 +354,27 @@ public abstract class MetaKeyKeyListener { * or locked meta key. */ public static final int getMetaState(long state) { - return getActive(state, META_SHIFT_ON, META_SHIFT_ON, META_CAP_LOCKED) | - getActive(state, META_ALT_ON, META_ALT_ON, META_ALT_LOCKED) | - getActive(state, META_SYM_ON, META_SYM_ON, META_SYM_LOCKED); + int result = 0; + + if ((state & META_CAP_LOCKED) != 0) { + result |= META_CAP_LOCKED; + } else if ((state & META_SHIFT_ON) != 0) { + result |= META_SHIFT_ON; + } + + if ((state & META_ALT_LOCKED) != 0) { + result |= META_ALT_LOCKED; + } else if ((state & META_ALT_ON) != 0) { + result |= META_ALT_ON; + } + + if ((state & META_SYM_LOCKED) != 0) { + result |= META_SYM_LOCKED; + } else if ((state & META_SYM_ON) != 0) { + result |= META_SYM_ON; + } + + return result; } /** @@ -348,29 +388,25 @@ public abstract class MetaKeyKeyListener { public static final int getMetaState(long state, int meta) { switch (meta) { case META_SHIFT_ON: - return getActive(state, meta, 1, 2); + if ((state & META_CAP_LOCKED) != 0) return 2; + if ((state & META_SHIFT_ON) != 0) return 1; + return 0; case META_ALT_ON: - return getActive(state, meta, 1, 2); + if ((state & META_ALT_LOCKED) != 0) return 2; + if ((state & META_ALT_ON) != 0) return 1; + return 0; case META_SYM_ON: - return getActive(state, meta, 1, 2); + if ((state & META_SYM_LOCKED) != 0) return 2; + if ((state & META_SYM_ON) != 0) return 1; + return 0; default: return 0; } } - private static int getActive(long state, int meta, int on, int lock) { - if ((state&(meta<<LOCKED_SHIFT)) != 0) { - return lock; - } else if ((state&meta) != 0) { - return on; - } else { - return 0; - } - } - /** * Call this method after you handle a keypress so that the meta * state will be reset to unshifted (if it is not still down) @@ -378,17 +414,23 @@ public abstract class MetaKeyKeyListener { * the current state, returns the new state. */ public static long adjustMetaAfterKeypress(long state) { - state = adjust(state, META_SHIFT_ON, META_SHIFT_MASK); - state = adjust(state, META_ALT_ON, META_ALT_MASK); - state = adjust(state, META_SYM_ON, META_SYM_MASK); - return state; - } + if ((state & META_CAP_PRESSED) != 0) { + state = (state & ~META_SHIFT_MASK) | META_SHIFT_ON | META_CAP_USED; + } else if ((state & META_CAP_RELEASED) != 0) { + state &= ~META_SHIFT_MASK; + } + + if ((state & META_ALT_PRESSED) != 0) { + state = (state & ~META_ALT_MASK) | META_ALT_ON | META_ALT_USED; + } else if ((state & META_ALT_RELEASED) != 0) { + state &= ~META_ALT_MASK; + } - private static long adjust(long state, int what, long mask) { - if ((state&(((long)what)<<PRESSED_SHIFT)) != 0) - return (state&~mask) | what | ((long)what)<<USED_SHIFT; - else if ((state&(((long)what)<<RELEASED_SHIFT)) != 0) - return state & ~mask; + if ((state & META_SYM_PRESSED) != 0) { + state = (state & ~META_SYM_MASK) | META_SYM_ON | META_SYM_USED; + } else if ((state & META_SYM_RELEASED) != 0) { + state &= ~META_SYM_MASK; + } return state; } @@ -397,32 +439,36 @@ public abstract class MetaKeyKeyListener { */ public static long handleKeyDown(long state, int keyCode, KeyEvent event) { if (keyCode == KeyEvent.KEYCODE_SHIFT_LEFT || keyCode == KeyEvent.KEYCODE_SHIFT_RIGHT) { - return press(state, META_SHIFT_ON, META_SHIFT_MASK); + return press(state, META_SHIFT_ON, META_SHIFT_MASK, + META_CAP_LOCKED, META_CAP_PRESSED, META_CAP_RELEASED, META_CAP_USED); } if (keyCode == KeyEvent.KEYCODE_ALT_LEFT || keyCode == KeyEvent.KEYCODE_ALT_RIGHT || keyCode == KeyEvent.KEYCODE_NUM) { - return press(state, META_ALT_ON, META_ALT_MASK); + return press(state, META_ALT_ON, META_ALT_MASK, + META_ALT_LOCKED, META_ALT_PRESSED, META_ALT_RELEASED, META_ALT_USED); } if (keyCode == KeyEvent.KEYCODE_SYM) { - return press(state, META_SYM_ON, META_SYM_MASK); + return press(state, META_SYM_ON, META_SYM_MASK, + META_SYM_LOCKED, META_SYM_PRESSED, META_SYM_RELEASED, META_SYM_USED); } - return state; } - private static long press(long state, int what, long mask) { - if ((state&(((long)what)<<PRESSED_SHIFT)) != 0) - ; // repeat before use - else if ((state&(((long)what)<<RELEASED_SHIFT)) != 0) - state = (state&~mask) | what | (((long)what) << LOCKED_SHIFT); - else if ((state&(((long)what)<<USED_SHIFT)) != 0) - ; // repeat after use - else if ((state&(((long)what)<<LOCKED_SHIFT)) != 0) - state = state&~mask; - else - state = state | what | (((long)what)<<PRESSED_SHIFT); + private static long press(long state, int what, long mask, + long locked, long pressed, long released, long used) { + if ((state & pressed) != 0) { + // repeat before use + } else if ((state & released) != 0) { + state = (state &~ mask) | what | locked; + } else if ((state & used) != 0) { + // repeat after use + } else if ((state & locked) != 0) { + state &= ~mask; + } else { + state |= what | pressed; + } return state; } @@ -431,39 +477,52 @@ public abstract class MetaKeyKeyListener { */ public static long handleKeyUp(long state, int keyCode, KeyEvent event) { if (keyCode == KeyEvent.KEYCODE_SHIFT_LEFT || keyCode == KeyEvent.KEYCODE_SHIFT_RIGHT) { - return release(state, META_SHIFT_ON, META_SHIFT_MASK); + return release(state, META_SHIFT_ON, META_SHIFT_MASK, + META_CAP_PRESSED, META_CAP_RELEASED, META_CAP_USED); } if (keyCode == KeyEvent.KEYCODE_ALT_LEFT || keyCode == KeyEvent.KEYCODE_ALT_RIGHT || keyCode == KeyEvent.KEYCODE_NUM) { - return release(state, META_ALT_ON, META_ALT_MASK); + return release(state, META_ALT_ON, META_ALT_MASK, + META_ALT_PRESSED, META_ALT_RELEASED, META_ALT_USED); } if (keyCode == KeyEvent.KEYCODE_SYM) { - return release(state, META_SYM_ON, META_SYM_MASK); + return release(state, META_SYM_ON, META_SYM_MASK, + META_SYM_PRESSED, META_SYM_RELEASED, META_SYM_USED); } - return state; } - private static long release(long state, int what, long mask) { - if ((state&(((long)what)<<USED_SHIFT)) != 0) - state = state&~mask; - else if ((state&(((long)what)<<PRESSED_SHIFT)) != 0) - state = state | what | (((long)what)<<RELEASED_SHIFT); + private static long release(long state, int what, long mask, + long pressed, long released, long used) { + if ((state & used) != 0) { + state &= ~mask; + } else if ((state & pressed) != 0) { + state |= what | released; + } return state; } + /** + * Clears the state of the specified meta key if it is locked. + * @param state the meta key state + * @param which meta keys to clear, may be a combination of {@link #META_SHIFT_ON}, + * {@link #META_ALT_ON} or {@link #META_SYM_ON}. + */ public long clearMetaKeyState(long state, int which) { - if ((which&META_SHIFT_ON) != 0) - state = resetLock(state, META_SHIFT_ON, META_SHIFT_MASK); - if ((which&META_ALT_ON) != 0) - state = resetLock(state, META_ALT_ON, META_ALT_MASK); - if ((which&META_SYM_ON) != 0) - state = resetLock(state, META_SYM_ON, META_SYM_MASK); + if ((which & META_SHIFT_ON_AND_LOCKED) == META_SHIFT_ON_AND_LOCKED) { + state &= ~META_SHIFT_MASK; + } + if ((which & META_ALT_ON_AND_LOCKED) == META_ALT_ON_AND_LOCKED) { + state &= ~META_ALT_MASK; + } + if ((which & META_SYM_ON_AND_LOCKED) == META_SYM_ON_AND_LOCKED) { + state &= ~META_SYM_MASK; + } return state; } - + /** * The meta key has been pressed but has not yet been used. */ diff --git a/core/java/android/text/method/Touch.java b/core/java/android/text/method/Touch.java index 3b98fc3..9eaab17 100644 --- a/core/java/android/text/method/Touch.java +++ b/core/java/android/text/method/Touch.java @@ -144,7 +144,7 @@ public class Touch { if (ds[0].mFarEnough) { ds[0].mUsed = true; boolean cap = (MetaKeyKeyListener.getMetaState(buffer, - KeyEvent.META_SHIFT_ON) == 1) || + MetaKeyKeyListener.META_SHIFT_ON) == 1) || (MetaKeyKeyListener.getMetaState(buffer, MetaKeyKeyListener.META_SELECTING) != 0); float dx; diff --git a/core/java/android/view/KeyEvent.java b/core/java/android/view/KeyEvent.java index 0e5ece1..0e75682 100755 --- a/core/java/android/view/KeyEvent.java +++ b/core/java/android/view/KeyEvent.java @@ -42,6 +42,13 @@ import android.view.KeyCharacterMap.KeyData; * Meta states describe the pressed state of key modifiers * such as {@link #META_SHIFT_ON} or {@link #META_ALT_ON}. * </p><p> + * Key codes typically correspond one-to-one with individual keys on an input device. + * Many keys and key combinations serve quite different functions on different + * input devices so care must be taken when interpreting them. Always use the + * {@link KeyCharacterMap} associated with the input device when mapping keys + * to characters. Be aware that there may be multiple key input devices active + * at the same time and each will have its own key character map. + * </p><p> * When interacting with an IME, the framework may deliver key events * with the special action {@link #ACTION_MULTIPLE} that either specifies * that single repeated key code or a sequence of characters to insert. @@ -209,7 +216,7 @@ public class KeyEvent extends InputEvent implements Parcelable { /** Key code constant: Enter key. */ public static final int KEYCODE_ENTER = 66; /** Key code constant: Backspace key. - * Deletes characters before the insertion point. */ + * Deletes characters before the insertion point, unlike {@link #KEYCODE_FORWARD_DEL}. */ public static final int KEYCODE_DEL = 67; /** Key code constant: '`' (backtick) key. */ public static final int KEYCODE_GRAVE = 68; @@ -331,6 +338,125 @@ public class KeyEvent extends InputEvent implements Parcelable { /** Key code constant: Mode Button key. * On a game controller, the button labeled Mode. */ public static final int KEYCODE_BUTTON_MODE = 110; + /** Key code constant: Escape key. */ + public static final int KEYCODE_ESCAPE = 111; + /** Key code constant: Forward Delete key. + * Deletes characters ahead of the insertion point, unlike {@link #KEYCODE_DEL}. */ + public static final int KEYCODE_FORWARD_DEL = 112; + /** Key code constant: Left Control modifier key. */ + public static final int KEYCODE_CTRL_LEFT = 113; + /** Key code constant: Right Control modifier key. */ + public static final int KEYCODE_CTRL_RIGHT = 114; + /** Key code constant: Caps Lock modifier key. */ + public static final int KEYCODE_CAPS_LOCK = 115; + /** Key code constant: Scroll Lock key. */ + public static final int KEYCODE_SCROLL_LOCK = 116; + /** Key code constant: Left Meta modifier key. */ + public static final int KEYCODE_META_LEFT = 117; + /** Key code constant: Right Meta modifier key. */ + public static final int KEYCODE_META_RIGHT = 118; + /** Key code constant: Function modifier key. */ + public static final int KEYCODE_FUNCTION = 119; + /** Key code constant: System Request / Print Screen key. */ + public static final int KEYCODE_SYSRQ = 120; + /** Key code constant: Break / Pause key. */ + public static final int KEYCODE_BREAK = 121; + /** Key code constant: Home Movement key. + * Used for scrolling or moving the cursor around to the start of a line + * or to the top of a list. */ + public static final int KEYCODE_MOVE_HOME = 122; + /** Key code constant: End Movement key. + * Used for scrolling or moving the cursor around to the end of a line + * or to the bottom of a list. */ + public static final int KEYCODE_MOVE_END = 123; + /** Key code constant: Insert key. + * Toggles insert / overwrite edit mode. */ + public static final int KEYCODE_INSERT = 124; + /** Key code constant: Forward key. + * Navigates forward in the history stack. Complement of {@link #KEYCODE_BACK}. */ + public static final int KEYCODE_FORWARD = 125; + /** Key code constant: Play media key. */ + public static final int KEYCODE_MEDIA_PLAY = 126; + /** Key code constant: Pause media key. */ + public static final int KEYCODE_MEDIA_PAUSE = 127; + /** Key code constant: Close media key. + * May be used to close a CD tray, for example. */ + public static final int KEYCODE_MEDIA_CLOSE = 128; + /** Key code constant: Eject media key. + * May be used to eject a CD tray, for example. */ + public static final int KEYCODE_MEDIA_EJECT = 129; + /** Key code constant: Record media key. */ + public static final int KEYCODE_MEDIA_RECORD = 130; + /** Key code constant: F1 key. */ + public static final int KEYCODE_F1 = 131; + /** Key code constant: F2 key. */ + public static final int KEYCODE_F2 = 132; + /** Key code constant: F3 key. */ + public static final int KEYCODE_F3 = 133; + /** Key code constant: F4 key. */ + public static final int KEYCODE_F4 = 134; + /** Key code constant: F5 key. */ + public static final int KEYCODE_F5 = 135; + /** Key code constant: F6 key. */ + public static final int KEYCODE_F6 = 136; + /** Key code constant: F7 key. */ + public static final int KEYCODE_F7 = 137; + /** Key code constant: F8 key. */ + public static final int KEYCODE_F8 = 138; + /** Key code constant: F9 key. */ + public static final int KEYCODE_F9 = 139; + /** Key code constant: F10 key. */ + public static final int KEYCODE_F10 = 140; + /** Key code constant: F11 key. */ + public static final int KEYCODE_F11 = 141; + /** Key code constant: F12 key. */ + public static final int KEYCODE_F12 = 142; + /** Key code constant: Num Lock modifier key. + * This is the Num Lock key; it is different from {@link #KEYCODE_NUM}. + * This key generally modifies the behavior of other keys on the numeric keypad. */ + public static final int KEYCODE_NUM_LOCK = 143; + /** Key code constant: Numeric keypad '0' key. */ + public static final int KEYCODE_NUMPAD_0 = 144; + /** Key code constant: Numeric keypad '1' key. */ + public static final int KEYCODE_NUMPAD_1 = 145; + /** Key code constant: Numeric keypad '2' key. */ + public static final int KEYCODE_NUMPAD_2 = 146; + /** Key code constant: Numeric keypad '3' key. */ + public static final int KEYCODE_NUMPAD_3 = 147; + /** Key code constant: Numeric keypad '4' key. */ + public static final int KEYCODE_NUMPAD_4 = 148; + /** Key code constant: Numeric keypad '5' key. */ + public static final int KEYCODE_NUMPAD_5 = 149; + /** Key code constant: Numeric keypad '6' key. */ + public static final int KEYCODE_NUMPAD_6 = 150; + /** Key code constant: Numeric keypad '7' key. */ + public static final int KEYCODE_NUMPAD_7 = 151; + /** Key code constant: Numeric keypad '8' key. */ + public static final int KEYCODE_NUMPAD_8 = 152; + /** Key code constant: Numeric keypad '9' key. */ + public static final int KEYCODE_NUMPAD_9 = 153; + /** Key code constant: Numeric keypad '/' key (for division). */ + public static final int KEYCODE_NUMPAD_DIVIDE = 154; + /** Key code constant: Numeric keypad '*' key (for multiplication). */ + public static final int KEYCODE_NUMPAD_MULTIPLY = 155; + /** Key code constant: Numeric keypad '-' key (for subtraction). */ + public static final int KEYCODE_NUMPAD_SUBTRACT = 156; + /** Key code constant: Numeric keypad '+' key (for addition). */ + public static final int KEYCODE_NUMPAD_ADD = 157; + /** Key code constant: Numeric keypad '.' key (for decimals or digit grouping). */ + public static final int KEYCODE_NUMPAD_DOT = 158; + /** Key code constant: Numeric keypad ',' key (for decimals or digit grouping). */ + public static final int KEYCODE_NUMPAD_COMMA = 159; + /** Key code constant: Numeric keypad Enter key. */ + public static final int KEYCODE_NUMPAD_ENTER = 160; + /** Key code constant: Numeric keypad '=' key. */ + public static final int KEYCODE_NUMPAD_EQUALS = 161; + /** Key code constant: Numeric keypad '(' key. */ + public static final int KEYCODE_NUMPAD_LEFT_PAREN = 162; + /** Key code constant: Numeric keypad ')' key. */ + public static final int KEYCODE_NUMPAD_RIGHT_PAREN = 163; + + private static final int LAST_KEYCODE = KEYCODE_NUMPAD_RIGHT_PAREN; // NOTE: If you add a new keycode here you must also add it to: // isSystem() @@ -339,7 +465,6 @@ public class KeyEvent extends InputEvent implements Parcelable { // external/webkit/WebKit/android/plugins/ANPKeyCodes.h // tools/puppet_master/PuppetMaster/nav_keys.py // frameworks/base/core/res/res/values/attrs.xml - // commands/monkey/Monkey.java // emulator? // // Also Android currently does not reserve code ranges for vendor- @@ -347,9 +472,213 @@ public class KeyEvent extends InputEvent implements Parcelable { // MUST contribute a patch to the open source project to define // those new codes. This is intended to maintain a consistent // set of key code definitions across all Android devices. - - private static final int LAST_KEYCODE = KEYCODE_BUTTON_MODE; - + + // Symbolic names of all keys indexed by keycode. + // There should be exactly LAST_KEYCODE + 1 entries in this table. + private static final String[] KEYCODE_SYMBOLIC_NAMES = new String[] { + "KEYCODE_UNKNOWN", + "KEYCODE_SOFT_LEFT", + "KEYCODE_SOFT_RIGHT", + "KEYCODE_HOME", + "KEYCODE_BACK", + "KEYCODE_CALL", + "KEYCODE_ENDCALL", + "KEYCODE_0", + "KEYCODE_1", + "KEYCODE_2", + "KEYCODE_3", + "KEYCODE_4", + "KEYCODE_5", + "KEYCODE_6", + "KEYCODE_7", + "KEYCODE_8", + "KEYCODE_9", + "KEYCODE_STAR", + "KEYCODE_POUND", + "KEYCODE_DPAD_UP", + "KEYCODE_DPAD_DOWN", + "KEYCODE_DPAD_LEFT", + "KEYCODE_DPAD_RIGHT", + "KEYCODE_DPAD_CENTER", + "KEYCODE_VOLUME_UP", + "KEYCODE_VOLUME_DOWN", + "KEYCODE_POWER", + "KEYCODE_CAMERA", + "KEYCODE_CLEAR", + "KEYCODE_A", + "KEYCODE_B", + "KEYCODE_C", + "KEYCODE_D", + "KEYCODE_E", + "KEYCODE_F", + "KEYCODE_G", + "KEYCODE_H", + "KEYCODE_I", + "KEYCODE_J", + "KEYCODE_K", + "KEYCODE_L", + "KEYCODE_M", + "KEYCODE_N", + "KEYCODE_O", + "KEYCODE_P", + "KEYCODE_Q", + "KEYCODE_R", + "KEYCODE_S", + "KEYCODE_T", + "KEYCODE_U", + "KEYCODE_V", + "KEYCODE_W", + "KEYCODE_X", + "KEYCODE_Y", + "KEYCODE_Z", + "KEYCODE_COMMA", + "KEYCODE_PERIOD", + "KEYCODE_ALT_LEFT", + "KEYCODE_ALT_RIGHT", + "KEYCODE_SHIFT_LEFT", + "KEYCODE_SHIFT_RIGHT", + "KEYCODE_TAB", + "KEYCODE_SPACE", + "KEYCODE_SYM", + "KEYCODE_EXPLORER", + "KEYCODE_ENVELOPE", + "KEYCODE_ENTER", + "KEYCODE_DEL", + "KEYCODE_GRAVE", + "KEYCODE_MINUS", + "KEYCODE_EQUALS", + "KEYCODE_LEFT_BRACKET", + "KEYCODE_RIGHT_BRACKET", + "KEYCODE_BACKSLASH", + "KEYCODE_SEMICOLON", + "KEYCODE_APOSTROPHE", + "KEYCODE_SLASH", + "KEYCODE_AT", + "KEYCODE_NUM", + "KEYCODE_HEADSETHOOK", + "KEYCODE_FOCUS", + "KEYCODE_PLUS", + "KEYCODE_MENU", + "KEYCODE_NOTIFICATION", + "KEYCODE_SEARCH", + "KEYCODE_MEDIA_PLAY_PAUSE", + "KEYCODE_MEDIA_STOP", + "KEYCODE_MEDIA_NEXT", + "KEYCODE_MEDIA_PREVIOUS", + "KEYCODE_MEDIA_REWIND", + "KEYCODE_MEDIA_FAST_FORWARD", + "KEYCODE_MUTE", + "KEYCODE_PAGE_UP", + "KEYCODE_PAGE_DOWN", + "KEYCODE_PICTSYMBOLS", + "KEYCODE_SWITCH_CHARSET", + "KEYCODE_BUTTON_A", + "KEYCODE_BUTTON_B", + "KEYCODE_BUTTON_C", + "KEYCODE_BUTTON_X", + "KEYCODE_BUTTON_Y", + "KEYCODE_BUTTON_Z", + "KEYCODE_BUTTON_L1", + "KEYCODE_BUTTON_R1", + "KEYCODE_BUTTON_L2", + "KEYCODE_BUTTON_R2", + "KEYCODE_BUTTON_THUMBL", + "KEYCODE_BUTTON_THUMBR", + "KEYCODE_BUTTON_START", + "KEYCODE_BUTTON_SELECT", + "KEYCODE_BUTTON_MODE", + "KEYCODE_ESCAPE", + "KEYCODE_FORWARD_DEL", + "KEYCODE_CTRL_LEFT", + "KEYCODE_CTRL_RIGHT", + "KEYCODE_CAPS_LOCK", + "KEYCODE_SCROLL_LOCK", + "KEYCODE_META_LEFT", + "KEYCODE_META_RIGHT", + "KEYCODE_FUNCTION", + "KEYCODE_SYSRQ", + "KEYCODE_BREAK", + "KEYCODE_MOVE_HOME", + "KEYCODE_MOVE_END", + "KEYCODE_INSERT", + "KEYCODE_FORWARD", + "KEYCODE_MEDIA_PLAY", + "KEYCODE_MEDIA_PAUSE", + "KEYCODE_MEDIA_CLOSE", + "KEYCODE_MEDIA_EJECT", + "KEYCODE_MEDIA_RECORD", + "KEYCODE_F1", + "KEYCODE_F2", + "KEYCODE_F3", + "KEYCODE_F4", + "KEYCODE_F5", + "KEYCODE_F6", + "KEYCODE_F7", + "KEYCODE_F8", + "KEYCODE_F9", + "KEYCODE_F10", + "KEYCODE_F11", + "KEYCODE_F12", + "KEYCODE_NUM_LOCK", + "KEYCODE_NUMPAD_0", + "KEYCODE_NUMPAD_1", + "KEYCODE_NUMPAD_2", + "KEYCODE_NUMPAD_3", + "KEYCODE_NUMPAD_4", + "KEYCODE_NUMPAD_5", + "KEYCODE_NUMPAD_6", + "KEYCODE_NUMPAD_7", + "KEYCODE_NUMPAD_8", + "KEYCODE_NUMPAD_9", + "KEYCODE_NUMPAD_DIVIDE", + "KEYCODE_NUMPAD_MULTIPLY", + "KEYCODE_MUMPAD_SUBTRACT", + "KEYCODE_NUMPAD_ADD", + "KEYCODE_NUMPAD_DOT", + "KEYCODE_NUMPAD_COMMA", + "KEYCODE_NUMPAD_ENTER", + "KEYCODE_NUMPAD_EQUALS", + "KEYCODE_NUMPAD_LEFT_PAREN", + "KEYCODE_NUMPAD_RIGHT_PAREN", + }; + + // Symbolic names of all metakeys in bit order from least significant to most significant. + // Accordingly there are exactly 32 values in this table. + private static final String[] META_SYMBOLIC_NAMES = new String[] { + "META_SHIFT_ON", + "META_ALT_ON", + "META_SYM_ON", + "META_FUNCTION_ON", + "META_ALT_LEFT_ON", + "META_ALT_RIGHT_ON", + "META_SHIFT_LEFT_ON", + "META_SHIFT_RIGHT_ON", + "META_CAP_LOCKED", + "META_ALT_LOCKED", + "META_SYM_LOCKED", + "0x00000800", + "META_CTRL_ON", + "META_CTRL_LEFT_ON", + "META_CTRL_RIGHT_ON", + "0x00008000", + "META_META_ON", + "META_META_LEFT_ON", + "META_META_RIGHT_ON", + "0x00080000", + "META_CAPS_LOCK_LATCHED", + "META_NUM_LOCK_LATCHED", + "META_SCROLL_LOCK_LATCHED", + "0x00800000", + "0x01000000", + "0x02000000", + "0x04000000", + "0x08000000", + "0x10000000", + "0x20000000", + "0x40000000", + "0x80000000", + }; + /** * @deprecated There are now more than MAX_KEYCODE keycodes. * Use {@link #getMaxKeyCode()} instead. @@ -377,6 +706,35 @@ public class KeyEvent extends InputEvent implements Parcelable { public static final int ACTION_MULTIPLE = 2; /** + * SHIFT key locked in CAPS mode. + * Reserved for use by {@link MetaKeyKeyListener} for a published constant in its API. + * @hide + */ + public static final int META_CAP_LOCKED = 0x100; + + /** + * ALT key locked. + * Reserved for use by {@link MetaKeyKeyListener} for a published constant in its API. + * @hide + */ + public static final int META_ALT_LOCKED = 0x200; + + /** + * SYM key locked. + * Reserved for use by {@link MetaKeyKeyListener} for a published constant in its API. + * @hide + */ + public static final int META_SYM_LOCKED = 0x400; + + /** + * Text is in selection mode. + * Reserved for use by {@link MetaKeyKeyListener} for a private unpublished constant + * in its API that is currently being retained for legacy reasons. + * @hide + */ + public static final int META_SELECTING = 0x800; + + /** * <p>This mask is used to check whether one of the ALT meta keys is pressed.</p> * * @see #isAltPressed() @@ -441,6 +799,97 @@ public class KeyEvent extends InputEvent implements Parcelable { public static final int META_SYM_ON = 0x4; /** + * <p>This mask is used to check whether the FUNCTION meta key is pressed.</p> + * + * @see #isFunctionPressed() + * @see #getMetaState() + */ + public static final int META_FUNCTION_ON = 0x8; + + /** + * <p>This mask is used to check whether one of the CTRL meta keys is pressed.</p> + * + * @see #isCtrlPressed() + * @see #getMetaState() + * @see #KEYCODE_CTRL_LEFT + * @see #KEYCODE_CTRL_RIGHT + */ + public static final int META_CTRL_ON = 0x1000; + + /** + * <p>This mask is used to check whether the left CTRL meta key is pressed.</p> + * + * @see #isCtrlPressed() + * @see #getMetaState() + * @see #KEYCODE_CTRL_LEFT + */ + public static final int META_CTRL_LEFT_ON = 0x2000; + + /** + * <p>This mask is used to check whether the right CTRL meta key is pressed.</p> + * + * @see #isCtrlPressed() + * @see #getMetaState() + * @see #KEYCODE_CTRL_RIGHT + */ + public static final int META_CTRL_RIGHT_ON = 0x4000; + + /** + * <p>This mask is used to check whether one of the META meta keys is pressed.</p> + * + * @see #isMetaPressed() + * @see #getMetaState() + * @see #KEYCODE_META_LEFT + * @see #KEYCODE_META_RIGHT + */ + public static final int META_META_ON = 0x10000; + + /** + * <p>This mask is used to check whether the left META meta key is pressed.</p> + * + * @see #isMetaPressed() + * @see #getMetaState() + * @see #KEYCODE_META_LEFT + */ + public static final int META_META_LEFT_ON = 0x20000; + + /** + * <p>This mask is used to check whether the right META meta key is pressed.</p> + * + * @see #isMetaPressed() + * @see #getMetaState() + * @see #KEYCODE_META_RIGHT + */ + public static final int META_META_RIGHT_ON = 0x40000; + + /** + * <p>This mask is used to check whether the CAPS LOCK meta key is latched.</p> + * + * @see #isCapsLockLatched() + * @see #getMetaState() + * @see #KEYCODE_CAPS_LOCK + */ + public static final int META_CAPS_LOCK_LATCHED = 0x100000; + + /** + * <p>This mask is used to check whether the NUM LOCK meta key is latched.</p> + * + * @see #isNumLockLatched() + * @see #getMetaState() + * @see #KEYCODE_NUM_LOCK + */ + public static final int META_NUM_LOCK_LATCHED = 0x200000; + + /** + * <p>This mask is used to check whether the SCROLL LOCK meta key is latched.</p> + * + * @see #isScrollLockLatched() + * @see #getMetaState() + * @see #KEYCODE_SCROLL_LOCK + */ + public static final int META_SCROLL_LOCK_LATCHED = 0x400000; + + /** * This mask is set if the device woke because of this key event. */ public static final int FLAG_WOKE_HERE = 0x1; @@ -603,6 +1052,17 @@ public class KeyEvent extends InputEvent implements Parcelable { boolean onKeyMultiple(int keyCode, int count, KeyEvent event); } + static { + if (META_SYMBOLIC_NAMES.length != 32) { + throw new IllegalStateException( + "META_SYMBOLIC_NAMES array should contain exactly 32 entries."); + } + if (KEYCODE_SYMBOLIC_NAMES.length != LAST_KEYCODE + 1) { + throw new IllegalStateException( + "KEYCODE_SYMBOLIC_NAMES array is out of sync with the keycode constants."); + } + } + /** * Create a new key event. * @@ -939,9 +1399,29 @@ public class KeyEvent extends InputEvent implements Parcelable { * @see #isAltPressed() * @see #isShiftPressed() * @see #isSymPressed() + * @see #isCtrlPressed() + * @see #isMetaPressed() + * @see #isFunctionPressed() + * @see #isCapsLockLatched() + * @see #isNumLockLatched() + * @see #isScrollLockLatched() * @see #META_ALT_ON + * @see #META_ALT_LEFT_ON + * @see #META_ALT_RIGHT_ON * @see #META_SHIFT_ON + * @see #META_SHIFT_LEFT_ON + * @see #META_SHIFT_RIGHT_ON * @see #META_SYM_ON + * @see #META_FUNCTION_ON + * @see #META_CTRL_ON + * @see #META_CTRL_LEFT_ON + * @see #META_CTRL_RIGHT_ON + * @see #META_META_ON + * @see #META_META_LEFT_ON + * @see #META_META_RIGHT_ON + * @see #META_CAPS_LOCK_LATCHED + * @see #META_NUM_LOCK_LATCHED + * @see #META_SCROLL_LOCK_LATCHED */ public final int getMetaState() { return mMetaState; @@ -961,13 +1441,28 @@ public class KeyEvent extends InputEvent implements Parcelable { * * @return whether the provided keyCode is one of * {@link #KEYCODE_SHIFT_LEFT} {@link #KEYCODE_SHIFT_RIGHT}, - * {@link #KEYCODE_ALT_LEFT}, {@link #KEYCODE_ALT_RIGHT} - * or {@link #KEYCODE_SYM}. + * {@link #KEYCODE_ALT_LEFT}, {@link #KEYCODE_ALT_RIGHT}, + * {@link #KEYCODE_SYM}, {@link #KEYCODE_NUM}, {@link #KEYCODE_FUNCTION}, + * {@link #KEYCODE_CTRL_LEFT}, {@link #KEYCODE_CTRL_RIGHT}, + * {@link #KEYCODE_META_LEFT}, or {@link #KEYCODE_META_RIGHT}. */ public static boolean isModifierKey(int keyCode) { - return keyCode == KEYCODE_SHIFT_LEFT || keyCode == KEYCODE_SHIFT_RIGHT - || keyCode == KEYCODE_ALT_LEFT || keyCode == KEYCODE_ALT_RIGHT - || keyCode == KEYCODE_SYM; + switch (keyCode) { + case KEYCODE_SHIFT_LEFT: + case KEYCODE_SHIFT_RIGHT: + case KEYCODE_ALT_LEFT: + case KEYCODE_ALT_RIGHT: + case KEYCODE_SYM: + case KEYCODE_NUM: + case KEYCODE_FUNCTION: + case KEYCODE_CTRL_LEFT: + case KEYCODE_CTRL_RIGHT: + case KEYCODE_META_LEFT: + case KEYCODE_META_RIGHT: + return true; + default: + return false; + } } /** @@ -1009,6 +1504,80 @@ public class KeyEvent extends InputEvent implements Parcelable { } /** + * <p>Returns the pressed state of the CTRL meta key.</p> + * + * @return true if the CTRL key is pressed, false otherwise + * + * @see #KEYCODE_CTRL_LEFT + * @see #KEYCODE_CTRL_RIGHT + * @see #META_CTRL_ON + */ + public final boolean isCtrlPressed() { + return (mMetaState & META_CTRL_ON) != 0; + } + + /** + * <p>Returns the pressed state of the META meta key.</p> + * + * @return true if the META key is pressed, false otherwise + * + * @see #KEYCODE_META_LEFT + * @see #KEYCODE_META_RIGHT + * @see #META_META_ON + */ + public final boolean isMetaPressed() { + return (mMetaState & META_META_ON) != 0; + } + + /** + * <p>Returns the pressed state of the FUNCTION meta key.</p> + * + * @return true if the FUNCTION key is pressed, false otherwise + * + * @see #KEYCODE_FUNCTION + * @see #META_FUNCTION_ON + */ + public final boolean isFunctionPressed() { + return (mMetaState & META_FUNCTION_ON) != 0; + } + + /** + * <p>Returns the latched state of the CAPS LOCK meta key.</p> + * + * @return true if the CAPS LOCK key is latched, false otherwise + * + * @see #KEYCODE_CAPS_LOCK + * @see #META_CAPS_LOCK_LATCHED + */ + public final boolean isCapsLockLatched() { + return (mMetaState & META_CAPS_LOCK_LATCHED) != 0; + } + + /** + * <p>Returns the latched state of the NUM LOCK meta key.</p> + * + * @return true if the NUM LOCK key is latched, false otherwise + * + * @see #KEYCODE_NUM_LOCK + * @see #META_NUM_LOCK_LATCHED + */ + public final boolean isNumLockLatched() { + return (mMetaState & META_NUM_LOCK_LATCHED) != 0; + } + + /** + * <p>Returns the latched state of the SCROLL LOCK meta key.</p> + * + * @return true if the SCROLL LOCK key is latched, false otherwise + * + * @see #KEYCODE_SCROLL_LOCK + * @see #META_SCROLL_LOCK_LATCHED + */ + public final boolean isScrollLockLatched() { + return (mMetaState & META_SCROLL_LOCK_LATCHED) != 0; + } + + /** * Retrieve the action of this key event. May be either * {@link #ACTION_DOWN}, {@link #ACTION_UP}, or {@link #ACTION_MULTIPLE}. * @@ -1392,12 +1961,118 @@ public class KeyEvent extends InputEvent implements Parcelable { } } } - + + @Override public String toString() { - return "KeyEvent{action=" + mAction + " code=" + mKeyCode - + " repeat=" + mRepeatCount - + " meta=" + mMetaState + " scancode=" + mScanCode - + " mFlags=" + mFlags + "}"; + return "KeyEvent{action=" + actionToString(mAction) + + " keycode=" + keyCodeToString(mKeyCode) + + " scancode=" + mScanCode + + " meta=" + metaStateToString(mMetaState) + + " flags=0x" + Integer.toHexString(mFlags) + + " repeat=" + mRepeatCount + + " device=" + mDeviceId + + " source=0x" + Integer.toHexString(mSource) + + "}"; + } + + /** + * Returns a string that represents the symbolic name of the specified action + * such as "ACTION_DOWN", or "35" (if unknown). + * + * @param action The action. + * @return The symbolic name of the specified action. + * @hide + */ + public static String actionToString(int action) { + switch (action) { + case ACTION_DOWN: + return "ACTION_DOWN"; + case ACTION_UP: + return "ACTION_UP"; + case ACTION_MULTIPLE: + return "ACTION_MULTIPLE"; + default: + return Integer.toString(action); + } + } + + /** + * Returns a string that represents the symbolic name of the specified keycode + * such as "KEYCODE_A", "KEYCODE_DPAD_UP", or "1001" (if unknown). + * + * @param keyCode The key code. + * @return The symbolic name of the specified keycode. + * + * @see KeyCharacterMap#getDisplayLabel + * @hide + */ + public static String keyCodeToString(int keyCode) { + if (keyCode >= 0 && keyCode < KEYCODE_SYMBOLIC_NAMES.length) { + return KEYCODE_SYMBOLIC_NAMES[keyCode]; + } + return Integer.toString(keyCode); + } + + /** + * Gets a keycode by its symbolic name such as "KEYCODE_A" or "1001" (if unknown). + * + * @param symbolicName The symbolic name of the keycode. + * @return The keycode or -1 if not found. + * @see #keycodeToString + * @hide + */ + public static int keyCodeFromString(String symbolicName) { + if (symbolicName == null) { + throw new IllegalArgumentException("symbolicName must not be null"); + } + + final int count = KEYCODE_SYMBOLIC_NAMES.length; + for (int i = 0; i < count; i++) { + if (symbolicName.equals(KEYCODE_SYMBOLIC_NAMES[i])) { + return i; + } + } + + try { + return Integer.parseInt(symbolicName,10); + } catch (NumberFormatException ex) { + return -1; + } + } + + /** + * Returns a string that represents the symbolic name of the specified combined meta + * key modifier state flags such as "0", "META_SHIFT_ON", + * "META_ALT_ON|META_SHIFT_ON" or "0x10000000" (if unknown). + * + * @param metaState The meta state. + * @return The symbolic name of the specified combined meta state flags. + * @hide + */ + public static String metaStateToString(int metaState) { + if (metaState == 0) { + return "0"; + } + StringBuilder result = null; + int i = 0; + while (metaState != 0) { + final boolean isSet = (metaState & 1) != 0; + metaState >>>= 1; // unsigned shift! + if (isSet) { + final String name = META_SYMBOLIC_NAMES[i]; + if (result == null) { + if (metaState == 0) { + return name; + } + result = new StringBuilder(name); + } else { + result.append('|'); + result.append(name); + } + } + i += 1; + } + return result.toString(); } public static final Parcelable.Creator<KeyEvent> CREATOR diff --git a/core/java/android/view/MotionEvent.java b/core/java/android/view/MotionEvent.java index 9411474..195d689 100644 --- a/core/java/android/view/MotionEvent.java +++ b/core/java/android/view/MotionEvent.java @@ -1550,8 +1550,54 @@ public final class MotionEvent extends InputEvent implements Parcelable { @Override public String toString() { return "MotionEvent{" + Integer.toHexString(System.identityHashCode(this)) - + " action=" + mAction + " x=" + getX() - + " y=" + getY() + " pressure=" + getPressure() + " size=" + getSize() + "}"; + + " action=" + actionToString(mAction) + + " x=" + getX() + + " y=" + getY() + + " pressure=" + getPressure() + + " size=" + getSize() + + " touchMajor=" + getTouchMajor() + + " touchMinor=" + getTouchMinor() + + " toolMajor=" + getToolMajor() + + " toolMinor=" + getToolMinor() + + " orientation=" + getOrientation() + + " meta=" + KeyEvent.metaStateToString(mMetaState) + + " pointerCount=" + getPointerCount() + + " historySize=" + getHistorySize() + + " flags=0x" + Integer.toHexString(mFlags) + + " edgeFlags=0x" + Integer.toHexString(mEdgeFlags) + + " device=" + mDeviceId + + " source=0x" + Integer.toHexString(mSource) + + "}"; + } + + /** + * Returns a string that represents the symbolic name of the specified action + * such as "ACTION_DOWN", "ACTION_POINTER_DOWN(3)" or "35" (if unknown). + * + * @param action The action. + * @return The symbolic name of the specified action. + * @hide + */ + public static String actionToString(int action) { + switch (action) { + case ACTION_DOWN: + return "ACTION_DOWN"; + case ACTION_UP: + return "ACTION_UP"; + case ACTION_CANCEL: + return "ACTION_CANCEL"; + case ACTION_MOVE: + return "ACTION_MOVE"; + } + int index = (action & ACTION_POINTER_INDEX_MASK) >> ACTION_POINTER_INDEX_SHIFT; + switch (action & ACTION_MASK) { + case ACTION_POINTER_DOWN: + return "ACTION_POINTER_DOWN(" + index + ")"; + case ACTION_POINTER_UP: + return "ACTION_POINTER_UP(" + index + ")"; + default: + return Integer.toString(action); + } } public static final Parcelable.Creator<MotionEvent> CREATOR diff --git a/core/res/res/values/attrs.xml b/core/res/res/values/attrs.xml index ef6d6cb..578191a 100755 --- a/core/res/res/values/attrs.xml +++ b/core/res/res/values/attrs.xml @@ -1056,6 +1056,59 @@ <enum name="KEYCODE_BUTTON_START" value="108" /> <enum name="KEYCODE_BUTTON_SELECT" value="109" /> <enum name="KEYCODE_BUTTON_MODE" value="110" /> + <enum name="KEYCODE_ESCAPE" value="111" /> + <enum name="KEYCODE_FORWARD_DEL" value="112" /> + <enum name="KEYCODE_CTRL_LEFT" value="113" /> + <enum name="KEYCODE_CTRL_RIGHT" value="114" /> + <enum name="KEYCODE_CAPS_LOCK" value="115" /> + <enum name="KEYCODE_SCROLL_LOCK" value="116" /> + <enum name="KEYCODE_META_LEFT" value="117" /> + <enum name="KEYCODE_META_RIGHT" value="118" /> + <enum name="KEYCODE_FUNCTION" value="119" /> + <enum name="KEYCODE_SYSRQ" value="120" /> + <enum name="KEYCODE_BREAK" value="121" /> + <enum name="KEYCODE_MOVE_HOME" value="122" /> + <enum name="KEYCODE_MOVE_END" value="123" /> + <enum name="KEYCODE_INSERT" value="124" /> + <enum name="KEYCODE_FORWARD" value="125" /> + <enum name="KEYCODE_MEDIA_PLAY" value="126" /> + <enum name="KEYCODE_MEDIA_PAUSE" value="127" /> + <enum name="KEYCODE_MEDIA_CLOSE" value="128" /> + <enum name="KEYCODE_MEDIA_EJECT" value="129" /> + <enum name="KEYCODE_MEDIA_RECORD" value="130" /> + <enum name="KEYCODE_F1" value="131" /> + <enum name="KEYCODE_F2" value="132" /> + <enum name="KEYCODE_F3" value="133" /> + <enum name="KEYCODE_F4" value="134" /> + <enum name="KEYCODE_F5" value="135" /> + <enum name="KEYCODE_F6" value="136" /> + <enum name="KEYCODE_F7" value="137" /> + <enum name="KEYCODE_F8" value="138" /> + <enum name="KEYCODE_F9" value="139" /> + <enum name="KEYCODE_F10" value="140" /> + <enum name="KEYCODE_F11" value="141" /> + <enum name="KEYCODE_F12" value="142" /> + <enum name="NUM_LOCK" value="143" /> + <enum name="NUMPAD_0" value="144" /> + <enum name="NUMPAD_1" value="145" /> + <enum name="NUMPAD_2" value="146" /> + <enum name="NUMPAD_3" value="147" /> + <enum name="NUMPAD_4" value="148" /> + <enum name="NUMPAD_5" value="149" /> + <enum name="NUMPAD_6" value="150" /> + <enum name="NUMPAD_7" value="151" /> + <enum name="NUMPAD_8" value="152" /> + <enum name="NUMPAD_9" value="153" /> + <enum name="NUMPAD_DIVIDE" value="154" /> + <enum name="NUMPAD_MULTIPLY" value="155" /> + <enum name="NUMPAD_SUBTRACT" value="156" /> + <enum name="NUMPAD_ADD" value="157" /> + <enum name="NUMPAD_DOT" value="158" /> + <enum name="NUMPAD_COMMA" value="159" /> + <enum name="NUMPAD_ENTER" value="160" /> + <enum name="NUMPAD_EQUALS" value="161" /> + <enum name="NUMPAD_LEFT_PAREN" value="162" /> + <enum name="NUMPAD_RIGHT_PAREN" value="163" /> </attr> <!-- ***************************************************************** --> diff --git a/data/keyboards/Android.mk b/data/keyboards/Android.mk new file mode 100644 index 0000000..7a0eae0 --- /dev/null +++ b/data/keyboards/Android.mk @@ -0,0 +1,27 @@ +# +# Copyright (C) 2010 The Android Open Source Project +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +# This makefile builds the key character map binary files. (*.kcm.bin) + +LOCAL_PATH := $(call my-dir) +include $(LOCAL_PATH)/common.mk + +$(foreach file,$(keycharmaps), \ + $(eval include $(CLEAR_VARS)) \ + $(eval LOCAL_SRC_FILES := $(file)) \ + $(eval LOCAL_MODULE_TAGS := optional) \ + $(eval include $(BUILD_KEY_CHAR_MAP)) \ +) diff --git a/data/keyboards/Generic.kcm b/data/keyboards/Generic.kcm new file mode 100644 index 0000000..f3c52a7 --- /dev/null +++ b/data/keyboards/Generic.kcm @@ -0,0 +1,100 @@ +# Copyright (C) 2010 The Android Open Source Project +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# +# Generic key character map for full alphabetic US English PC style external keyboards. +# +# This file is intentionally very generic and is intended to support a broad rang of keyboards. +# Do not edit the generic key character map to support a specific keyboard; instead, create +# a new key character map file with the required keyboard configuration. +# + +[type=QWERTY] + +# keycode display number base caps fn caps_fn + +A 'A' '2' 'a' 'A' 'a' 'A' +B 'B' '2' 'b' 'B' 'b' 'B' +C 'C' '2' 'c' 'C' 'c' 'C' +D 'D' '3' 'd' 'D' 'd' 'D' +E 'E' '3' 'e' 'E' 'e' 'E' +F 'F' '3' 'f' 'F' 'f' 'F' +G 'G' '4' 'g' 'G' 'g' 'G' +H 'H' '4' 'h' 'H' 'h' 'H' +I 'I' '4' 'i' 'I' 'i' 'I' +J 'J' '5' 'j' 'J' 'j' 'J' +K 'K' '5' 'k' 'K' 'k' 'K' +L 'L' '5' 'l' 'L' 'l' 'L' +M 'M' '6' 'm' 'M' 'm' 'M' +N 'N' '6' 'n' 'N' 'n' 'N' +O 'O' '6' 'o' 'O' 'o' 'O' +P 'P' '7' 'p' 'P' 'p' 'P' +Q 'Q' '7' 'q' 'Q' 'q' 'Q' +R 'R' '7' 'r' 'R' 'r' 'R' +S 'S' '7' 's' 'S' 's' 'S' +T 'T' '8' 't' 'T' 't' 'T' +U 'U' '8' 'u' 'U' 'u' 'U' +V 'V' '8' 'v' 'V' 'v' 'V' +W 'W' '9' 'w' 'W' 'w' 'W' +X 'X' '9' 'x' 'X' 'x' 'X' +Y 'Y' '9' 'y' 'Y' 'y' 'Y' +Z 'Z' '9' 'z' 'Z' 'z' 'Z' + +0 '0' '0' '0' ')' '0' ')' +1 '1' '1' '1' '!' '1' '!' +2 '2' '2' '2' '@' '2' '@' +3 '3' '3' '3' '#' '3' '#' +4 '4' '4' '4' '$' '4' '$' +5 '5' '5' '5' '%' '5' '%' +6 '6' '6' '6' '^' '6' '^' +7 '7' '7' '7' '&' '7' '&' +8 '8' '8' '8' '*' '8' '*' +9 '9' '9' '9' '(' '9' '(' + +SPACE 0x20 0x20 0x20 0x20 0x20 0x20 +ENTER 0xa 0xa 0xa 0xa 0xa 0xa +TAB 0x9 0x9 0x9 0x9 0x9 0x9 + +COMMA ',' ',' ',' '<' ',' '<' +PERIOD '.' '.' '.' '>' '.' '>' +SLASH '/' '/' '/' '?' '/' '?' +GRAVE '`' '`' '`' '~' '`' '~' +MINUS '-' '-' '-' '_' '-' '_' +EQUALS '=' '=' '=' '+' '=' '+' +LEFT_BRACKET '[' '[' '[' '{' '[' '{' +RIGHT_BRACKET ']' ']' ']' '}' ']' '}' +BACKSLASH '\' '\' '\' '|' '\' '|' +SEMICOLON ';' ';' ';' ':' ';' ':' +APOSTROPHE ''' ''' ''' '"' ''' '"' + +NUMPAD_0 '0' '0' '0' '0' '0' '0' +NUMPAD_1 '1' '1' '1' '1' '1' '1' +NUMPAD_2 '2' '2' '2' '2' '2' '2' +NUMPAD_3 '3' '3' '3' '3' '3' '3' +NUMPAD_4 '4' '4' '4' '4' '4' '4' +NUMPAD_5 '5' '5' '5' '5' '5' '5' +NUMPAD_6 '6' '6' '6' '6' '6' '6' +NUMPAD_7 '7' '7' '7' '7' '7' '7' +NUMPAD_8 '8' '8' '8' '8' '8' '8' +NUMPAD_9 '9' '9' '9' '9' '9' '9' +NUMPAD_LEFT_PAREN '(' '(' '(' '(' '(' '(' +NUMPAD_RIGHT_PAREN ')' ')' ')' ')' ')' ')' +NUMPAD_DIVIDE '/' '/' '/' '/' '/' '/' +NUMPAD_MULTIPLY '*' '*' '*' '*' '*' '*' +NUMPAD_SUBTRACT '-' '-' '-' '-' '-' '-' +NUMPAD_ADD '+' '+' '+' '+' '+' '+' +NUMPAD_DOT '.' '.' '.' '.' '.' '.' +NUMPAD_COMMA ',' ',' ',' ',' ',' ',' +NUMPAD_EQUALS '=' '=' '=' '=' '=' '=' +NUMPAD_ENTER 0xa 0xa 0xa 0xa 0xa 0xa diff --git a/data/keyboards/Generic.kl b/data/keyboards/Generic.kl new file mode 100644 index 0000000..818397b --- /dev/null +++ b/data/keyboards/Generic.kl @@ -0,0 +1,384 @@ +# Copyright (C) 2010 The Android Open Source Project +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# +# Generic key layout file for full alphabetic US English PC style external keyboards. +# +# This file is intentionally very generic and is intended to support a broad rang of keyboards. +# Do not edit the generic key layout to support a specific keyboard; instead, create +# a new key layout file with the required keyboard configuration. +# + +key 1 ESCAPE +key 2 1 +key 3 2 +key 4 3 +key 5 4 +key 6 5 +key 7 6 +key 8 7 +key 9 8 +key 10 9 +key 11 0 +key 12 MINUS +key 13 EQUALS +key 14 DEL +key 15 TAB +key 16 Q +key 17 W +key 18 E +key 19 R +key 20 T +key 21 Y +key 22 U +key 23 I +key 24 O +key 25 P +key 26 LEFT_BRACKET +key 27 RIGHT_BRACKET +key 28 ENTER +key 29 CTRL_LEFT +key 30 A +key 31 S +key 32 D +key 33 F +key 34 G +key 35 H +key 36 J +key 37 K +key 38 L +key 39 SEMICOLON +key 40 APOSTROPHE +key 41 GRAVE +key 42 SHIFT_LEFT +key 43 BACKSLASH +key 44 Z +key 45 X +key 46 C +key 47 V +key 48 B +key 49 N +key 50 M +key 51 COMMA +key 52 PERIOD +key 53 SLASH +key 54 SHIFT_RIGHT +key 55 NUMPAD_MULTIPLY +key 56 ALT_LEFT +key 57 SPACE +key 58 CAPS_LOCK +key 59 F1 +key 60 F2 +key 61 F3 +key 62 F4 +key 63 F5 +key 64 F6 +key 65 F7 +key 66 F8 +key 67 F9 +key 68 F10 +key 69 NUM_LOCK +key 70 SCROLL_LOCK +key 71 NUMPAD_7 +key 72 NUMPAD_8 +key 73 NUMPAD_9 +key 74 NUMPAD_SUBTRACT +key 75 NUMPAD_4 +key 76 NUMPAD_5 +key 77 NUMPAD_6 +key 78 NUMPAD_ADD +key 79 NUMPAD_1 +key 80 NUMPAD_2 +key 81 NUMPAD_3 +key 82 NUMPAD_0 +key 83 NUMPAD_DOT +# key 84 (undefined) +# key 85 "KEY_ZENKAKUHANKAKU" +# key 86 "KEY_102ND" +key 87 F11 +key 88 F12 +# key 89 "KEY_RO" +# key 90 "KEY_KATAKANA" +# key 91 "KEY_HIRAGANA" +# key 92 "KEY_HENKAN" +# key 93 "KEY_KATAKANAHIRAGANA" +# key 94 "KEY_MUHENKAN" +key 95 NUMPAD_COMMA +key 96 NUMPAD_ENTER +key 97 CTRL_RIGHT +key 98 NUMPAD_DIVIDE +key 99 SYSRQ +key 100 ALT_RIGHT +# key 101 "KEY_LINEFEED" +key 102 MOVE_HOME +key 103 DPAD_UP +key 104 PAGE_UP +key 105 DPAD_LEFT +key 106 DPAD_RIGHT +key 107 MOVE_END +key 108 DPAD_DOWN +key 109 PAGE_DOWN +key 110 INSERT +key 111 FORWARD_DEL +# key 112 "KEY_MACRO" +key 113 MUTE +key 114 VOLUME_DOWN +key 115 VOLUME_UP +key 116 POWER WAKE +key 117 NUMPAD_EQUALS +# key 118 "KEY_KPPLUSMINUS" +key 119 BREAK +# key 120 (undefined) +key 121 NUMPAD_COMMA +# key 122 "KEY_HANGEUL" +# key 123 "KEY_HANJA" +# key 124 "KEY_YEN" +key 125 META_LEFT +key 126 META_RIGHT +key 127 MENU WAKE_DROPPED +key 128 MEDIA_STOP +# key 129 "KEY_AGAIN" +# key 130 "KEY_PROPS" +# key 131 "KEY_UNDO" +# key 132 "KEY_FRONT" +# key 133 "KEY_COPY" +# key 134 "KEY_OPEN" +# key 135 "KEY_PASTE" +# key 136 "KEY_FIND" +# key 137 "KEY_CUT" +# key 138 "KEY_HELP" +key 139 MENU WAKE_DROPPED +# key 140 "KEY_CALC" +# key 141 "KEY_SETUP" +# key 142 "KEY_SLEEP" +# key 143 "KEY_WAKEUP" +# key 144 "KEY_FILE" +# key 145 "KEY_SENDFILE" +# key 146 "KEY_DELETEFILE" +# key 147 "KEY_XFER" +# key 148 "KEY_PROG1" +# key 149 "KEY_PROG2" +key 150 EXPLORER +# key 151 "KEY_MSDOS" +# key 152 "KEY_COFFEE" +# key 153 "KEY_DIRECTION" +# key 154 "KEY_CYCLEWINDOWS" +key 155 ENVELOPE +# key 156 "KEY_BOOKMARKS" +# key 157 "KEY_COMPUTER" +key 158 BACK WAKE_DROPPED +key 159 FORWARD +key 160 MEDIA_CLOSE +key 161 MEDIA_EJECT +key 162 MEDIA_EJECT +key 163 MEDIA_NEXT +key 164 MEDIA_PLAY_PAUSE +key 165 MEDIA_PREVIOUS +key 166 MEDIA_STOP +key 167 MEDIA_RECORD +key 168 MEDIA_REWIND +key 169 CALL +# key 170 "KEY_ISO" +# key 171 "KEY_CONFIG" +key 172 HOME +# key 173 "KEY_REFRESH" +# key 174 "KEY_EXIT" +# key 175 "KEY_MOVE" +# key 176 "KEY_EDIT" +key 177 PAGE_UP +key 178 PAGE_DOWN +key 179 NUMPAD_LEFT_PAREN +key 180 NUMPAD_RIGHT_PAREN +# key 181 "KEY_NEW" +# key 182 "KEY_REDO" +# key 183 F13 +# key 184 F14 +# key 185 F15 +# key 186 F16 +# key 187 F17 +# key 188 F18 +# key 189 F19 +# key 190 F20 +# key 191 F21 +# key 192 F22 +# key 193 F23 +# key 194 F24 +# key 195 (undefined) +# key 196 (undefined) +# key 197 (undefined) +# key 198 (undefined) +# key 199 (undefined) +key 200 MEDIA_PLAY +key 201 MEDIA_PAUSE +# key 202 "KEY_PROG3" +# key 203 "KEY_PROG4" +# key 204 (undefined) +# key 205 "KEY_SUSPEND" +# key 206 "KEY_CLOSE" +key 207 MEDIA_PLAY +key 208 MEDIA_FAST_FORWARD +# key 209 "KEY_BASSBOOST" +# key 210 "KEY_PRINT" +# key 211 "KEY_HP" +key 212 CAMERA +# key 213 "KEY_SOUND" +# key 214 "KEY_QUESTION" +key 215 ENVELOPE +# key 216 "KEY_CHAT" +key 217 SEARCH +# key 218 "KEY_CONNECT" +# key 219 "KEY_FINANCE" +# key 220 "KEY_SPORT" +# key 221 "KEY_SHOP" +# key 222 "KEY_ALTERASE" +# key 223 "KEY_CANCEL" +# key 224 "KEY_BRIGHTNESSDOWN" +# key 225 "KEY_BRIGHTNESSUP" +key 226 HEADSETHOOK +key 227 STAR +key 228 POUND +key 229 SOFT_LEFT +key 230 SOFT_RIGHT +key 231 CALL +key 232 DPAD_CENTER +key 233 HEADSETHOOK +# key 234 "KEY_0_5" or "KEY_SAVE" +# key 235 "KEY_2_5" or "KEY_DOCUMENTS" +# key 236 "KEY_SWITCHVIDEOMODE" or "KEY_BATTERY" +# key 237 "KEY_KBDILLUMTOGGLE" +# key 238 "KEY_KBDILLUMDOWN" +# key 239 "KEY_KBDILLUMUP" +# key 240 "KEY_UNKNOWN" + + +key 304 BUTTON_A +key 305 BUTTON_B +key 306 BUTTON_C +key 307 BUTTON_X +key 308 BUTTON_Y +key 309 BUTTON_Z +key 310 BUTTON_L1 +key 311 BUTTON_R1 +key 312 BUTTON_L2 +key 313 BUTTON_R2 +key 314 BUTTON_SELECT +key 315 BUTTON_START +key 316 BUTTON_MODE +key 317 BUTTON_THUMBL +key 318 BUTTON_THUMBR + + +# key 352 "KEY_OK" +# key 353 "KEY_SELECT" +# key 354 "KEY_GOTO" +# key 355 "KEY_CLEAR" +# key 356 "KEY_POWER2" +# key 357 "KEY_OPTION" +# key 358 "KEY_INFO" +# key 359 "KEY_TIME" +# key 360 "KEY_VENDOR" +# key 361 "KEY_ARCHIVE" +# key 362 "KEY_PROGRAM" +# key 363 "KEY_CHANNEL" +# key 364 "KEY_FAVORITES" +# key 365 "KEY_EPG" +# key 366 "KEY_PVR" +# key 367 "KEY_MHP" +# key 368 "KEY_LANGUAGE" +# key 369 "KEY_TITLE" +# key 370 "KEY_SUBTITLE" +# key 371 "KEY_ANGLE" +# key 372 "KEY_ZOOM" +# key 373 "KEY_MODE" +# key 374 "KEY_KEYBOARD" +# key 375 "KEY_SCREEN" +# key 376 "KEY_PC" +# key 377 "KEY_TV" +# key 378 "KEY_TV2" +# key 379 "KEY_VCR" +# key 380 "KEY_VCR2" +# key 381 "KEY_SAT" +# key 382 "KEY_SAT2" +# key 383 "KEY_CD" +# key 384 "KEY_TAPE" +# key 385 "KEY_RADIO" +# key 386 "KEY_TUNER" +# key 387 "KEY_PLAYER" +# key 388 "KEY_TEXT" +# key 389 "KEY_DVD" +# key 390 "KEY_AUX" +# key 391 "KEY_MP3" +# key 392 "KEY_AUDIO" +# key 393 "KEY_VIDEO" +# key 394 "KEY_DIRECTORY" +# key 395 "KEY_LIST" +# key 396 "KEY_MEMO" +# key 397 "KEY_CALENDAR" +# key 398 "KEY_RED" +# key 399 "KEY_GREEN" +# key 400 "KEY_YELLOW" +# key 401 "KEY_BLUE" +# key 402 "KEY_CHANNELUP" +# key 403 "KEY_CHANNELDOWN" +# key 404 "KEY_FIRST" +# key 405 "KEY_LAST" +# key 406 "KEY_AB" +# key 407 "KEY_NEXT" +# key 408 "KEY_RESTART" +# key 409 "KEY_SLOW" +# key 410 "KEY_SHUFFLE" +# key 411 "KEY_BREAK" +# key 412 "KEY_PREVIOUS" +# key 413 "KEY_DIGITS" +# key 414 "KEY_TEEN" +# key 415 "KEY_TWEN" + + +# key 448 "KEY_DEL_EOL" +# key 449 "KEY_DEL_EOS" +# key 450 "KEY_INS_LINE" +# key 451 "KEY_DEL_LINE" + + +key 464 FUNCTION +key 465 ESCAPE FUNCTION +key 466 F1 FUNCTION +key 467 F2 FUNCTION +key 468 F3 FUNCTION +key 469 F4 FUNCTION +key 470 F5 FUNCTION +key 471 F6 FUNCTION +key 472 F7 FUNCTION +key 473 F8 FUNCTION +key 474 F9 FUNCTION +key 475 F10 FUNCTION +key 476 F11 FUNCTION +key 477 F12 FUNCTION +key 478 1 FUNCTION +key 479 2 FUNCTION +key 480 D FUNCTION +key 481 E FUNCTION +key 482 F FUNCTION +key 483 S FUNCTION +key 484 B FUNCTION + + +# key 497 KEY_BRL_DOT1 +# key 498 KEY_BRL_DOT2 +# key 499 KEY_BRL_DOT3 +# key 500 KEY_BRL_DOT4 +# key 501 KEY_BRL_DOT5 +# key 502 KEY_BRL_DOT6 +# key 503 KEY_BRL_DOT7 +# key 504 KEY_BRL_DOT8 diff --git a/data/keyboards/Motorola_Bluetooth_Wireless_Keyboard.kcm b/data/keyboards/Motorola_Bluetooth_Wireless_Keyboard.kcm new file mode 100644 index 0000000..0f31683 --- /dev/null +++ b/data/keyboards/Motorola_Bluetooth_Wireless_Keyboard.kcm @@ -0,0 +1,71 @@ +# Copyright (C) 2010 The Android Open Source Project +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +[type=QWERTY] + +# keycode display number base caps fn caps_fn + +A 'A' '2' 'a' 'A' 'a' 'A' +B 'B' '2' 'b' 'B' 'b' 'B' +C 'C' '2' 'c' 'C' 'c' 'C' +D 'D' '3' 'd' 'D' 'd' 'D' +E 'E' '3' 'e' 'E' 'e' 'E' +F 'F' '3' 'f' 'F' 'f' 'F' +G 'G' '4' 'g' 'G' 'g' 'G' +H 'H' '4' 'h' 'H' 'h' 'H' +I 'I' '4' 'i' 'I' 'i' 'I' +J 'J' '5' 'j' 'J' 'j' 'J' +K 'K' '5' 'k' 'K' 'k' 'K' +L 'L' '5' 'l' 'L' 'l' 'L' +M 'M' '6' 'm' 'M' 'm' 'M' +N 'N' '6' 'n' 'N' 'n' 'N' +O 'O' '6' 'o' 'O' 'o' 'O' +P 'P' '7' 'p' 'P' 'p' 'P' +Q 'Q' '7' 'q' 'Q' 'q' 'Q' +R 'R' '7' 'r' 'R' 'r' 'R' +S 'S' '7' 's' 'S' 's' 'S' +T 'T' '8' 't' 'T' 't' 'T' +U 'U' '8' 'u' 'U' 'u' 'U' +V 'V' '8' 'v' 'V' 'v' 'V' +W 'W' '9' 'w' 'W' 'w' 'W' +X 'X' '9' 'x' 'X' 'x' 'X' +Y 'Y' '9' 'y' 'Y' 'y' 'Y' +Z 'Z' '9' 'z' 'Z' 'z' 'Z' + +0 '0' '0' '0' ')' '0' ')' +1 '1' '1' '1' '!' '1' '!' +2 '2' '2' '2' '@' '2' '@' +3 '3' '3' '3' '#' '3' '#' +4 '4' '4' '4' '$' '4' '$' +5 '5' '5' '5' '%' '5' '%' +6 '6' '6' '6' '^' '6' '^' +7 '7' '7' '7' '&' '7' '&' +8 '8' '8' '8' '*' '8' '*' +9 '9' '9' '9' '(' '9' '(' + +SPACE 0x20 0x20 0x20 0x20 0x20 0x20 +ENTER 0xa 0xa 0xa 0xa 0xa 0xa +TAB 0x9 0x9 0x9 0x9 0x9 0x9 + +COMMA ',' ',' ',' '<' ',' '<' +PERIOD '.' '.' '.' '>' '.' '>' +SLASH '/' '/' '/' '?' '/' '?' +GRAVE '`' '`' '`' '~' '`' '~' +MINUS '-' '-' '-' '_' '-' '_' +EQUALS '=' '=' '=' '+' '=' '+' +LEFT_BRACKET '[' '[' '[' '{' '[' '{' +RIGHT_BRACKET ']' ']' ']' '}' ']' '}' +BACKSLASH '\' '\' '\' '|' '\' '|' +SEMICOLON ';' ';' ';' ':' ';' ':' +APOSTROPHE ''' ''' ''' '"' ''' '"' diff --git a/data/keyboards/Motorola_Bluetooth_Wireless_Keyboard.kl b/data/keyboards/Motorola_Bluetooth_Wireless_Keyboard.kl new file mode 100644 index 0000000..1298d53 --- /dev/null +++ b/data/keyboards/Motorola_Bluetooth_Wireless_Keyboard.kl @@ -0,0 +1,96 @@ +# Copyright (C) 2010 The Android Open Source Project +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +key 1 BACK +key 2 1 +key 3 2 +key 4 3 +key 5 4 +key 6 5 +key 7 6 +key 8 7 +key 9 8 +key 10 9 +key 11 0 +key 12 MINUS +key 13 EQUALS +key 14 DEL +key 15 TAB +key 16 Q +key 17 W +key 18 E +key 19 R +key 20 T +key 21 Y +key 22 U +key 23 I +key 24 O +key 25 P +key 26 LEFT_BRACKET +key 27 RIGHT_BRACKET +key 28 ENTER +key 29 CTRL_LEFT +key 30 A +key 31 S +key 32 D +key 33 F +key 34 G +key 35 H +key 36 J +key 37 K +key 38 L +key 39 SEMICOLON +key 40 APOSTROPHE +key 41 GRAVE +key 42 SHIFT_LEFT +key 43 BACKSLASH +key 44 Z +key 45 X +key 46 C +key 47 V +key 48 B +key 49 N +key 50 M +key 51 COMMA +key 52 PERIOD +key 53 SLASH +key 54 SHIFT_RIGHT +key 57 SPACE +key 58 CAPS_LOCK +key 59 F1 +key 60 F2 +key 61 F3 +key 62 F4 +key 63 F5 +key 64 F6 +key 65 F7 +key 66 F8 +key 67 F9 +key 97 CTRL_RIGHT +key 102 HOME +key 103 DPAD_UP +key 105 DPAD_LEFT +key 106 DPAD_RIGHT +key 107 MOVE_END +key 110 INSERT +key 111 FORWARD_DEL +key 113 MUTE +key 114 VOLUME_DOWN +key 115 VOLUME_UP +key 125 MENU +key 127 SEARCH +key 163 MEDIA_NEXT +key 164 MEDIA_PLAY_PAUSE +key 165 MEDIA_PREVIOUS +key 166 MEDIA_STOP diff --git a/data/keyboards/common.mk b/data/keyboards/common.mk new file mode 100644 index 0000000..7a58b07 --- /dev/null +++ b/data/keyboards/common.mk @@ -0,0 +1,24 @@ +# Copyright (C) 2010 The Android Open Source Project +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# This is the list of keylayouts and key character maps to build. +# Used by Android.mk and keyboards.mk. + +keylayouts := \ + Generic.kl \ + Motorola_Bluetooth_Wireless_Keyboard.kl + +keycharmaps := \ + Generic.kcm \ + Motorola_Bluetooth_Wireless_Keyboard.kcm diff --git a/data/keyboards/keyboards.mk b/data/keyboards/keyboards.mk new file mode 100644 index 0000000..665c8bf --- /dev/null +++ b/data/keyboards/keyboards.mk @@ -0,0 +1,22 @@ +# Copyright (C) 2010 The Android Open Source Project +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. + +# Warning: this is actually a product definition, to be inherited from + +include $(LOCAL_PATH)/common.mk + +PRODUCT_COPY_FILES := $(foreach file,$(keylayouts),\ + frameworks/base/data/keyboards/$(file):system/usr/keylayout/$(file)) + +PRODUCT_PACKAGES := $(keycharmaps) diff --git a/include/ui/EventHub.h b/include/ui/EventHub.h index d78e35f..1431964 100644 --- a/include/ui/EventHub.h +++ b/include/ui/EventHub.h @@ -187,6 +187,9 @@ public: virtual bool markSupportedKeyCodes(int32_t deviceId, size_t numCodes, const int32_t* keyCodes, uint8_t* outFlags) const = 0; + virtual bool hasLed(int32_t deviceId, int32_t led) const = 0; + virtual void setLedState(int32_t deviceId, int32_t led, bool on) = 0; + virtual void dump(String8& dump) = 0; }; @@ -198,9 +201,9 @@ public: status_t errorCheck() const; virtual uint32_t getDeviceClasses(int32_t deviceId) const; - + virtual String8 getDeviceName(int32_t deviceId) const; - + virtual status_t getAbsoluteAxisInfo(int32_t deviceId, int axis, RawAbsoluteAxisInfo* outAxisInfo) const; @@ -218,6 +221,9 @@ public: virtual bool getEvent(RawEvent* outEvent); + virtual bool hasLed(int32_t deviceId, int32_t led) const; + virtual void setLedState(int32_t deviceId, int32_t led, bool on); + virtual void dump(String8& dump); protected: @@ -240,7 +246,10 @@ private: uint32_t classes; uint8_t* keyBitmask; KeyLayoutMap* layoutMap; - String8 keylayoutFilename; + String8 keyMapName; + bool defaultKeyMap; + String8 keyLayoutFilename; + String8 keyCharacterMapFilename; int fd; device_t* next; @@ -250,13 +259,19 @@ private: device_t* getDeviceLocked(int32_t deviceId) const; bool hasKeycodeLocked(device_t* device, int keycode) const; - + int32_t getScanCodeStateLocked(device_t* device, int32_t scanCode) const; int32_t getKeyCodeStateLocked(device_t* device, int32_t keyCode) const; int32_t getSwitchStateLocked(device_t* device, int32_t sw) const; bool markSupportedKeyCodesLocked(device_t* device, size_t numCodes, const int32_t* keyCodes, uint8_t* outFlags) const; + void configureKeyMap(device_t* device); + bool probeKeyMap(device_t* device, const String8& keyMapName, bool defaultKeyMap); + void selectKeyMap(device_t* device, const String8& keyMapName, bool defaultKeyMap); + void setKeyboardProperties(device_t* device, bool firstKeyboard); + void clearKeyboardProperties(device_t* device, bool firstKeyboard); + // Protect all internal state. mutable Mutex mLock; diff --git a/include/ui/Input.h b/include/ui/Input.h index 8c6018b..1355bab 100644 --- a/include/ui/Input.h +++ b/include/ui/Input.h @@ -76,7 +76,7 @@ namespace android { */ enum { /* These flags originate in RawEvents and are generally set in the key map. - * See also labels for policy flags in KeycodeLabels.h. */ + * NOTE: If you edit these flags, also edit labels in KeycodeLabels.h. */ POLICY_FLAG_WAKE = 0x00000001, POLICY_FLAG_WAKE_DROPPED = 0x00000002, @@ -87,6 +87,7 @@ enum { POLICY_FLAG_MENU = 0x00000040, POLICY_FLAG_LAUNCHER = 0x00000080, POLICY_FLAG_VIRTUAL = 0x00000100, + POLICY_FLAG_FUNCTION = 0x00000200, POLICY_FLAG_RAW_MASK = 0x0000ffff, diff --git a/include/ui/InputReader.h b/include/ui/InputReader.h index c15e382..a1b59e6 100644 --- a/include/ui/InputReader.h +++ b/include/ui/InputReader.h @@ -419,9 +419,18 @@ private: Vector<KeyDown> keyDowns; // keys that are down int32_t metaState; nsecs_t downTime; // time of most recent key down + + struct LedState { + bool avail; // led is available + bool on; // we think the led is currently on + }; + LedState capsLockLedState; + LedState numLockLedState; + LedState scrollLockLedState; } mLocked; void initializeLocked(); + void initializeLedStateLocked(LockedState::LedState& ledState, int32_t led); bool isKeyboardOrGamepadKey(int32_t scanCode); @@ -429,6 +438,10 @@ private: uint32_t policyFlags); ssize_t findKeyDownLocked(int32_t scanCode); + + void updateLedStateLocked(bool reset); + void updateLedStateForModifierLocked(LockedState::LedState& ledState, int32_t led, + int32_t modifier, bool reset); }; diff --git a/include/ui/KeycodeLabels.h b/include/ui/KeycodeLabels.h index f71d9cd..ef2b6b3 100755 --- a/include/ui/KeycodeLabels.h +++ b/include/ui/KeycodeLabels.h @@ -135,6 +135,59 @@ static const KeycodeLabel KEYCODES[] = { { "BUTTON_START", 108 }, { "BUTTON_SELECT", 109 }, { "BUTTON_MODE", 110 }, + { "ESCAPE", 111 }, + { "FORWARD_DEL", 112 }, + { "CTRL_LEFT", 113 }, + { "CTRL_RIGHT", 114 }, + { "CAPS_LOCK", 115 }, + { "SCROLL_LOCK", 116 }, + { "META_LEFT", 117 }, + { "META_RIGHT", 118 }, + { "FUNCTION", 119 }, + { "SYSRQ", 120 }, + { "BREAK", 121 }, + { "MOVE_HOME", 122 }, + { "MOVE_END", 123 }, + { "INSERT", 124 }, + { "FORWARD", 125 }, + { "MEDIA_PLAY", 126 }, + { "MEDIA_PAUSE", 127 }, + { "MEDIA_CLOSE", 128 }, + { "MEDIA_EJECT", 129 }, + { "MEDIA_RECORD", 130 }, + { "F1", 131 }, + { "F2", 132 }, + { "F3", 133 }, + { "F4", 134 }, + { "F5", 135 }, + { "F6", 136 }, + { "F7", 137 }, + { "F8", 138 }, + { "F9", 139 }, + { "F10", 140 }, + { "F11", 141 }, + { "F12", 142 }, + { "NUM_LOCK", 143 }, + { "NUMPAD_0", 144 }, + { "NUMPAD_1", 145 }, + { "NUMPAD_2", 146 }, + { "NUMPAD_3", 147 }, + { "NUMPAD_4", 148 }, + { "NUMPAD_5", 149 }, + { "NUMPAD_6", 150 }, + { "NUMPAD_7", 151 }, + { "NUMPAD_8", 152 }, + { "NUMPAD_9", 153 }, + { "NUMPAD_DIVIDE", 154 }, + { "NUMPAD_MULTIPLY", 155 }, + { "NUMPAD_SUBTRACT", 156 }, + { "NUMPAD_ADD", 157 }, + { "NUMPAD_DOT", 158 }, + { "NUMPAD_COMMA", 159 }, + { "NUMPAD_ENTER", 160 }, + { "NUMPAD_EQUALS", 161 }, + { "NUMPAD_LEFT_PAREN", 162 }, + { "NUMPAD_RIGHT_PAREN", 163 }, // NOTE: If you add a new keycode here you must also add it to several other files. // Refer to frameworks/base/core/java/android/view/KeyEvent.java for the full list. @@ -142,7 +195,7 @@ static const KeycodeLabel KEYCODES[] = { { NULL, 0 } }; -// See also policy flags in Input.h. +// NOTE: If you edit these flags, also edit policy flags in Input.h. static const KeycodeLabel FLAGS[] = { { "WAKE", 0x00000001 }, { "WAKE_DROPPED", 0x00000002 }, @@ -153,6 +206,7 @@ static const KeycodeLabel FLAGS[] = { { "MENU", 0x00000040 }, { "LAUNCHER", 0x00000080 }, { "VIRTUAL", 0x00000100 }, + { "FUNCTION", 0x00000200 }, { NULL, 0 } }; diff --git a/include/utils/String8.h b/include/utils/String8.h index ef0b51a..cef8eca 100644 --- a/include/utils/String8.h +++ b/include/utils/String8.h @@ -157,9 +157,12 @@ public: inline size_t size() const; inline size_t length() const; inline size_t bytes() const; + inline bool isEmpty() const; inline const SharedBuffer* sharedBuffer() const; + void clear(); + void setTo(const String8& other); status_t setTo(const char* other); status_t setTo(const char* other, size_t numChars); @@ -345,6 +348,11 @@ inline size_t String8::size() const return length(); } +inline bool String8::isEmpty() const +{ + return length() == 0; +} + inline size_t String8::bytes() const { return SharedBuffer::sizeFromData(mString)-1; diff --git a/libs/ui/EventHub.cpp b/libs/ui/EventHub.cpp index 944731d..97a7528 100644 --- a/libs/ui/EventHub.cpp +++ b/libs/ui/EventHub.cpp @@ -94,7 +94,7 @@ static inline const char* toString(bool value) { EventHub::device_t::device_t(int32_t _id, const char* _path, const char* name) : id(_id), path(_path), name(name), classes(0) - , keyBitmask(NULL), layoutMap(new KeyLayoutMap()), fd(-1), next(NULL) { + , keyBitmask(NULL), layoutMap(new KeyLayoutMap()), defaultKeyMap(false), fd(-1), next(NULL) { } EventHub::device_t::~device_t() { @@ -103,7 +103,7 @@ EventHub::device_t::~device_t() { } EventHub::EventHub(void) - : mError(NO_INIT), mHaveFirstKeyboard(false), mFirstKeyboardId(0) + : mError(NO_INIT), mHaveFirstKeyboard(false), mFirstKeyboardId(-1) , mDevicesById(0), mNumDevicesById(0) , mOpeningDevices(0), mClosingDevices(0) , mDevices(0), mFDs(0), mFDCount(0), mOpened(false), mNeedToSendFinishedDeviceScan(false) @@ -325,6 +325,39 @@ void EventHub::addExcludedDevice(const char* deviceName) mExcludedDevices.push_back(name); } +bool EventHub::hasLed(int32_t deviceId, int32_t led) const { + AutoMutex _l(mLock); + device_t* device = getDeviceLocked(deviceId); + if (device) { + uint8_t bitmask[sizeof_bit_array(LED_MAX + 1)]; + memset(bitmask, 0, sizeof(bitmask)); + if (ioctl(device->fd, EVIOCGBIT(EV_LED, sizeof(bitmask)), bitmask) >= 0) { + if (test_bit(led, bitmask)) { + return true; + } + } + } + return false; +} + +void EventHub::setLedState(int32_t deviceId, int32_t led, bool on) { + AutoMutex _l(mLock); + device_t* device = getDeviceLocked(deviceId); + if (device) { + struct input_event ev; + ev.time.tv_sec = 0; + ev.time.tv_usec = 0; + ev.type = EV_LED; + ev.code = led; + ev.value = on ? 1 : 0; + + ssize_t nWrite; + do { + nWrite = write(device->fd, &ev, sizeof(struct input_event)); + } while (nWrite == -1 && errno == EINTR); + } +} + EventHub::device_t* EventHub::getDeviceLocked(int32_t deviceId) const { if (deviceId == 0) deviceId = mFirstKeyboardId; @@ -760,54 +793,42 @@ int EventHub::openDevice(const char *deviceName) { #endif if ((device->classes & INPUT_DEVICE_CLASS_KEYBOARD) != 0) { - char tmpfn[sizeof(name)]; - char keylayoutFilename[300]; - // a more descriptive name device->name = name; - // replace all the spaces with underscores - strcpy(tmpfn, name); - for (char *p = strchr(tmpfn, ' '); p && *p; p = strchr(tmpfn, ' ')) - *p = '_'; - - // find the .kl file we need for this device - const char* root = getenv("ANDROID_ROOT"); - snprintf(keylayoutFilename, sizeof(keylayoutFilename), - "%s/usr/keylayout/%s.kl", root, tmpfn); - bool defaultKeymap = false; - if (access(keylayoutFilename, R_OK)) { - snprintf(keylayoutFilename, sizeof(keylayoutFilename), - "%s/usr/keylayout/%s", root, "qwerty.kl"); - defaultKeymap = true; - } - status_t status = device->layoutMap->load(keylayoutFilename); - if (status) { - LOGE("Error %d loading key layout.", status); - } + // Configure the keymap for the device. + configureKeyMap(device); - // tell the world about the devname (the descriptive name) - if (!mHaveFirstKeyboard && !defaultKeymap && strstr(name, "-keypad")) { + // Tell the world about the devname (the descriptive name) + if (!mHaveFirstKeyboard && !device->defaultKeyMap && strstr(name, "-keypad")) { // the built-in keyboard has a well-known device ID of 0, // this device better not go away. mHaveFirstKeyboard = true; mFirstKeyboardId = device->id; - property_set("hw.keyboards.0.devname", name); + setKeyboardProperties(device, true); } else { // ensure mFirstKeyboardId is set to -something-. - if (mFirstKeyboardId == 0) { + if (mFirstKeyboardId == -1) { mFirstKeyboardId = device->id; + setKeyboardProperties(device, true); + } + } + setKeyboardProperties(device, false); + + // Load the keylayout. + if (!device->keyLayoutFilename.isEmpty()) { + status_t status = device->layoutMap->load(device->keyLayoutFilename); + if (status) { + LOGE("Error %d loading key layout file '%s'.", status, + device->keyLayoutFilename.string()); } } - char propName[100]; - sprintf(propName, "hw.keyboards.%u.devname", device->id); - property_set(propName, name); // 'Q' key support = cheap test of whether this is an alpha-capable kbd if (hasKeycodeLocked(device, AKEYCODE_Q)) { device->classes |= INPUT_DEVICE_CLASS_ALPHAKEY; } - + // See if this device has a DPAD. if (hasKeycodeLocked(device, AKEYCODE_DPAD_UP) && hasKeycodeLocked(device, AKEYCODE_DPAD_DOWN) && @@ -816,7 +837,7 @@ int EventHub::openDevice(const char *deviceName) { hasKeycodeLocked(device, AKEYCODE_DPAD_CENTER)) { device->classes |= INPUT_DEVICE_CLASS_DPAD; } - + // See if this device has a gamepad. for (size_t i = 0; i < sizeof(GAMEPAD_KEYCODES); i++) { if (hasKeycodeLocked(device, GAMEPAD_KEYCODES[i])) { @@ -825,8 +846,9 @@ int EventHub::openDevice(const char *deviceName) { } } - LOGI("New keyboard: device->id=0x%x devname='%s' propName='%s' keylayout='%s'\n", - device->id, name, propName, keylayoutFilename); + LOGI("New keyboard: device->id=0x%x devname='%s' keylayout='%s' keycharactermap='%s'\n", + device->id, name, + device->keyLayoutFilename.string(), device->keyCharacterMapFilename.string()); } // If the device isn't recognized as something we handle, don't monitor it. @@ -852,6 +874,109 @@ int EventHub::openDevice(const char *deviceName) { return 0; } +void EventHub::configureKeyMap(device_t* device) { + // As an initial key map name, try using the device name. + String8 keyMapName(device->name); + char* p = keyMapName.lockBuffer(keyMapName.size()); + while (*p) { + if (*p == ' ') *p = '_'; + p++; + } + keyMapName.unlockBuffer(); + + if (probeKeyMap(device, keyMapName, false)) return; + + // TODO Consider allowing the user to configure a specific key map somehow. + + // Try the Generic key map. + // TODO Apply some additional heuristics here to figure out what kind of + // generic key map to use (US English, etc.). + keyMapName.setTo("Generic"); + if (probeKeyMap(device, keyMapName, true)) return; + + // Fall back on the old style catchall qwerty key map. + keyMapName.setTo("qwerty"); + if (probeKeyMap(device, keyMapName, true)) return; + + // Give up! + keyMapName.setTo("unknown"); + selectKeyMap(device, keyMapName, true); + LOGE("Could not determine key map for device '%s'.", device->name.string()); +} + +bool EventHub::probeKeyMap(device_t* device, const String8& keyMapName, bool defaultKeyMap) { + const char* root = getenv("ANDROID_ROOT"); + + // TODO Consider also looking somewhere in a writeable partition like /data for a + // custom keymap supplied by the user for this device. + bool haveKeyLayout = !device->keyLayoutFilename.isEmpty(); + if (!haveKeyLayout) { + device->keyLayoutFilename.setTo(root); + device->keyLayoutFilename.append("/usr/keylayout/"); + device->keyLayoutFilename.append(keyMapName); + device->keyLayoutFilename.append(".kl"); + if (access(device->keyLayoutFilename.string(), R_OK)) { + device->keyLayoutFilename.clear(); + } else { + haveKeyLayout = true; + } + } + + bool haveKeyCharacterMap = !device->keyCharacterMapFilename.isEmpty(); + if (!haveKeyCharacterMap) { + device->keyCharacterMapFilename.setTo(root); + device->keyCharacterMapFilename.append("/usr/keychars/"); + device->keyCharacterMapFilename.append(keyMapName); + device->keyCharacterMapFilename.append(".kcm.bin"); + if (access(device->keyCharacterMapFilename.string(), R_OK)) { + device->keyCharacterMapFilename.clear(); + } else { + haveKeyCharacterMap = true; + } + } + + if (haveKeyLayout || haveKeyCharacterMap) { + selectKeyMap(device, keyMapName, defaultKeyMap); + } + return haveKeyLayout && haveKeyCharacterMap; +} + +void EventHub::selectKeyMap(device_t* device, + const String8& keyMapName, bool defaultKeyMap) { + if (device->keyMapName.isEmpty()) { + device->keyMapName.setTo(keyMapName); + device->defaultKeyMap = defaultKeyMap; + } +} + +void EventHub::setKeyboardProperties(device_t* device, bool firstKeyboard) { + int32_t id = firstKeyboard ? 0 : device->id; + + char propName[100]; + sprintf(propName, "hw.keyboards.%u.devname", id); + property_set(propName, device->name.string()); + sprintf(propName, "hw.keyboards.%u.keymap", id); + property_set(propName, device->keyMapName.string()); + sprintf(propName, "hw.keyboards.%u.klfile", id); + property_set(propName, device->keyLayoutFilename.string()); + sprintf(propName, "hw.keyboards.%u.kcmfile", id); + property_set(propName, device->keyCharacterMapFilename.string()); +} + +void EventHub::clearKeyboardProperties(device_t* device, bool firstKeyboard) { + int32_t id = firstKeyboard ? 0 : device->id; + + char propName[100]; + sprintf(propName, "hw.keyboards.%u.devname", id); + property_set(propName, ""); + sprintf(propName, "hw.keyboards.%u.keymap", id); + property_set(propName, ""); + sprintf(propName, "hw.keyboards.%u.klfile", id); + property_set(propName, ""); + sprintf(propName, "hw.keyboards.%u.kcmfile", id); + property_set(propName, ""); +} + bool EventHub::hasKeycodeLocked(device_t* device, int keycode) const { if (device->keyBitmask == NULL || device->layoutMap == NULL) { @@ -909,13 +1034,10 @@ int EventHub::closeDevice(const char *deviceName) { if (device->id == mFirstKeyboardId) { LOGW("built-in keyboard device %s (id=%d) is closing! the apps will not like this", device->path.string(), mFirstKeyboardId); - mFirstKeyboardId = 0; - property_set("hw.keyboards.0.devname", NULL); + mFirstKeyboardId = -1; + clearKeyboardProperties(device, true); } - // clear the property - char propName[100]; - sprintf(propName, "hw.keyboards.%u.devname", device->id); - property_set(propName, NULL); + clearKeyboardProperties(device, false); return 0; } } @@ -1014,7 +1136,11 @@ void EventHub::dump(String8& dump) { } dump.appendFormat(INDENT3 "Classes: 0x%08x\n", device->classes); dump.appendFormat(INDENT3 "Path: %s\n", device->path.string()); - dump.appendFormat(INDENT3 "KeyLayoutFile: %s\n", device->keylayoutFilename.string()); + dump.appendFormat(INDENT3 "KeyMapName: %s\n", device->keyMapName.string()); + dump.appendFormat(INDENT3 "KeyLayoutFilename: %s\n", + device->keyLayoutFilename.string()); + dump.appendFormat(INDENT3 "KeyCharacterMapFilename: %s\n", + device->keyCharacterMapFilename.string()); } } } // release lock diff --git a/libs/ui/InputReader.cpp b/libs/ui/InputReader.cpp index 0560bb8..6225121 100644 --- a/libs/ui/InputReader.cpp +++ b/libs/ui/InputReader.cpp @@ -70,41 +70,73 @@ static inline const char* toString(bool value) { return value ? "true" : "false"; } +int32_t setEphemeralMetaState(int32_t mask, bool down, int32_t oldMetaState) { + int32_t newMetaState; + if (down) { + newMetaState = oldMetaState | mask; + } else { + newMetaState = oldMetaState & + ~(mask | AMETA_ALT_ON | AMETA_SHIFT_ON | AMETA_CTRL_ON | AMETA_META_ON); + } + + if (newMetaState & (AMETA_ALT_LEFT_ON | AMETA_ALT_RIGHT_ON)) { + newMetaState |= AMETA_ALT_ON; + } + + if (newMetaState & (AMETA_SHIFT_LEFT_ON | AMETA_SHIFT_RIGHT_ON)) { + newMetaState |= AMETA_SHIFT_ON; + } + + if (newMetaState & (AMETA_CTRL_LEFT_ON | AMETA_CTRL_RIGHT_ON)) { + newMetaState |= AMETA_CTRL_ON; + } + + if (newMetaState & (AMETA_META_LEFT_ON | AMETA_META_RIGHT_ON)) { + newMetaState |= AMETA_META_ON; + } + return newMetaState; +} + +int32_t toggleLockedMetaState(int32_t mask, bool down, int32_t oldMetaState) { + if (down) { + return oldMetaState; + } else { + return oldMetaState ^ mask; + } +} int32_t updateMetaState(int32_t keyCode, bool down, int32_t oldMetaState) { int32_t mask; switch (keyCode) { case AKEYCODE_ALT_LEFT: - mask = AMETA_ALT_LEFT_ON; - break; + return setEphemeralMetaState(AMETA_ALT_LEFT_ON, down, oldMetaState); case AKEYCODE_ALT_RIGHT: - mask = AMETA_ALT_RIGHT_ON; - break; + return setEphemeralMetaState(AMETA_ALT_RIGHT_ON, down, oldMetaState); case AKEYCODE_SHIFT_LEFT: - mask = AMETA_SHIFT_LEFT_ON; - break; + return setEphemeralMetaState(AMETA_SHIFT_LEFT_ON, down, oldMetaState); case AKEYCODE_SHIFT_RIGHT: - mask = AMETA_SHIFT_RIGHT_ON; - break; + return setEphemeralMetaState(AMETA_SHIFT_RIGHT_ON, down, oldMetaState); case AKEYCODE_SYM: - mask = AMETA_SYM_ON; - break; + return setEphemeralMetaState(AMETA_SYM_ON, down, oldMetaState); + case AKEYCODE_FUNCTION: + return setEphemeralMetaState(AMETA_FUNCTION_ON, down, oldMetaState); + case AKEYCODE_CTRL_LEFT: + return setEphemeralMetaState(AMETA_CTRL_LEFT_ON, down, oldMetaState); + case AKEYCODE_CTRL_RIGHT: + return setEphemeralMetaState(AMETA_CTRL_RIGHT_ON, down, oldMetaState); + case AKEYCODE_META_LEFT: + return setEphemeralMetaState(AMETA_META_LEFT_ON, down, oldMetaState); + case AKEYCODE_META_RIGHT: + return setEphemeralMetaState(AMETA_META_RIGHT_ON, down, oldMetaState); + case AKEYCODE_CAPS_LOCK: + return toggleLockedMetaState(AMETA_CAPS_LOCK_LATCHED, down, oldMetaState); + case AKEYCODE_NUM_LOCK: + return toggleLockedMetaState(AMETA_NUM_LOCK_LATCHED, down, oldMetaState); + case AKEYCODE_SCROLL_LOCK: + return toggleLockedMetaState(AMETA_SCROLL_LOCK_LATCHED, down, oldMetaState); default: return oldMetaState; } - - int32_t newMetaState = down ? oldMetaState | mask : oldMetaState & ~ mask - & ~ (AMETA_ALT_ON | AMETA_SHIFT_ON); - - if (newMetaState & (AMETA_ALT_LEFT_ON | AMETA_ALT_RIGHT_ON)) { - newMetaState |= AMETA_ALT_ON; - } - - if (newMetaState & (AMETA_SHIFT_LEFT_ON | AMETA_SHIFT_RIGHT_ON)) { - newMetaState |= AMETA_SHIFT_ON; - } - - return newMetaState; } static const int32_t keyCodeRotationMap[][4] = { @@ -842,6 +874,17 @@ KeyboardInputMapper::~KeyboardInputMapper() { void KeyboardInputMapper::initializeLocked() { mLocked.metaState = AMETA_NONE; mLocked.downTime = 0; + + initializeLedStateLocked(mLocked.capsLockLedState, LED_CAPSL); + initializeLedStateLocked(mLocked.numLockLedState, LED_NUML); + initializeLedStateLocked(mLocked.scrollLockLedState, LED_SCROLLL); + + updateLedStateLocked(true); +} + +void KeyboardInputMapper::initializeLedStateLocked(LockedState::LedState& ledState, int32_t led) { + ledState.avail = getEventHub()->hasLed(getDeviceId(), led); + ledState.on = false; } uint32_t KeyboardInputMapper::getSources() { @@ -966,6 +1009,7 @@ void KeyboardInputMapper::processKey(nsecs_t when, bool down, int32_t keyCode, if (oldMetaState != newMetaState) { mLocked.metaState = newMetaState; metaStateChanged = true; + updateLedStateLocked(false); } downTime = mLocked.downTime; @@ -975,6 +1019,9 @@ void KeyboardInputMapper::processKey(nsecs_t when, bool down, int32_t keyCode, getContext()->updateGlobalMetaState(); } + if (policyFlags & POLICY_FLAG_FUNCTION) { + newMetaState |= AMETA_FUNCTION_ON; + } getDispatcher()->notifyKey(when, getDeviceId(), AINPUT_SOURCE_KEYBOARD, policyFlags, down ? AKEY_EVENT_ACTION_DOWN : AKEY_EVENT_ACTION_UP, AKEY_EVENT_FLAG_FROM_SYSTEM, keyCode, scanCode, newMetaState, downTime); @@ -1010,6 +1057,26 @@ int32_t KeyboardInputMapper::getMetaState() { } // release lock } +void KeyboardInputMapper::updateLedStateLocked(bool reset) { + updateLedStateForModifierLocked(mLocked.capsLockLedState, LED_CAPSL, + AMETA_CAPS_LOCK_LATCHED, reset); + updateLedStateForModifierLocked(mLocked.numLockLedState, LED_NUML, + AMETA_NUM_LOCK_LATCHED, reset); + updateLedStateForModifierLocked(mLocked.scrollLockLedState, LED_SCROLLL, + AMETA_SCROLL_LOCK_LATCHED, reset); +} + +void KeyboardInputMapper::updateLedStateForModifierLocked(LockedState::LedState& ledState, + int32_t led, int32_t modifier, bool reset) { + if (ledState.avail) { + bool desiredState = (mLocked.metaState & modifier) != 0; + if (ledState.on != desiredState) { + getEventHub()->setLedState(getDeviceId(), led, desiredState); + ledState.on = desiredState; + } + } +} + // --- TrackballInputMapper --- diff --git a/libs/ui/KeyCharacterMap.cpp b/libs/ui/KeyCharacterMap.cpp index e891181..870a45c 100644 --- a/libs/ui/KeyCharacterMap.cpp +++ b/libs/ui/KeyCharacterMap.cpp @@ -156,26 +156,38 @@ KeyCharacterMap::find_key(int keycode) KeyCharacterMap* KeyCharacterMap::load(int id) { - KeyCharacterMap* rv = NULL; + KeyCharacterMap* map; char path[PATH_MAX]; char propName[100]; char dev[PROPERTY_VALUE_MAX]; - char tmpfn[PROPERTY_VALUE_MAX]; + char fn[PROPERTY_VALUE_MAX]; int err; + + // Check whether the EventHub has set a key character map filename for us already. + sprintf(propName, "hw.keyboards.%u.kcmfile", id); + err = property_get(propName, fn, ""); + if (err > 0) { + map = try_file(fn); + if (map) { + return map; + } + LOGW("Error loading keycharmap file '%s'. %s='%s'", path, propName, fn); + } + + // Try using the device name. const char* root = getenv("ANDROID_ROOT"); sprintf(propName, "hw.keyboards.%u.devname", id); err = property_get(propName, dev, ""); if (err > 0) { // replace all the spaces with underscores - strcpy(tmpfn, dev); - for (char *p = strchr(tmpfn, ' '); p && *p; p = strchr(tmpfn, ' ')) + strcpy(fn, dev); + for (char *p = strchr(fn, ' '); p && *p; p = strchr(p + 1, ' ')) *p = '_'; - snprintf(path, sizeof(path), "%s/usr/keychars/%s.kcm.bin", root, tmpfn); - //LOGD("load: dev='%s' path='%s'\n", dev, path); - rv = try_file(path); - if (rv != NULL) { - return rv; + snprintf(path, sizeof(path), "%s/usr/keychars/%s.kcm.bin", root, fn); + map = try_file(path); + if (map) { + return map; } LOGW("Error loading keycharmap file '%s'. %s='%s'", path, propName, dev); } else { @@ -183,14 +195,14 @@ KeyCharacterMap::load(int id) } snprintf(path, sizeof(path), "%s/usr/keychars/qwerty.kcm.bin", root); - rv = try_file(path); - if (rv == NULL) { - LOGE("Can't find any keycharmaps (also tried %s)", path); - return NULL; + map = try_file(path); + if (map) { + LOGW("Using default keymap: %s", path); + return map; } - LOGW("Using default keymap: %s", path); - return rv; + LOGE("Can't find any keycharmaps (also tried %s)", path); + return NULL; } KeyCharacterMap* diff --git a/libs/utils/String8.cpp b/libs/utils/String8.cpp index 1c4f80c..6358fc4 100644 --- a/libs/utils/String8.cpp +++ b/libs/utils/String8.cpp @@ -292,6 +292,11 @@ String8::~String8() SharedBuffer::bufferFromData(mString)->release(); } +void String8::clear() { + SharedBuffer::bufferFromData(mString)->release(); + mString = getEmptyString(); +} + void String8::setTo(const String8& other) { SharedBuffer::bufferFromData(other.mString)->acquire(); diff --git a/native/include/android/input.h b/native/include/android/input.h index 5580700..d190e49 100644 --- a/native/include/android/input.h +++ b/native/include/android/input.h @@ -93,7 +93,37 @@ enum { AMETA_SHIFT_RIGHT_ON = 0x80, /* This mask is used to check whether the SYM meta key is pressed. */ - AMETA_SYM_ON = 0x04 + AMETA_SYM_ON = 0x04, + + /* This mask is used to check whether the FUNCTION meta key is pressed. */ + AMETA_FUNCTION_ON = 0x08, + + /* This mask is used to check whether one of the CTRL meta keys is pressed. */ + AMETA_CTRL_ON = 0x1000, + + /* This mask is used to check whether the left CTRL meta key is pressed. */ + AMETA_CTRL_LEFT_ON = 0x2000, + + /* This mask is used to check whether the right CTRL meta key is pressed. */ + AMETA_CTRL_RIGHT_ON = 0x4000, + + /* This mask is used to check whether one of the META meta keys is pressed. */ + AMETA_META_ON = 0x10000, + + /* This mask is used to check whether the left META meta key is pressed. */ + AMETA_META_LEFT_ON = 0x20000, + + /* This mask is used to check whether the right META meta key is pressed. */ + AMETA_META_RIGHT_ON = 0x40000, + + /* This mask is used to check whether the CAPS LOCK meta key is latched. */ + AMETA_CAPS_LOCK_LATCHED = 0x100000, + + /* This mask is used to check whether the NUM LOCK meta key is latched. */ + AMETA_NUM_LOCK_LATCHED = 0x200000, + + /* This mask is used to check whether the SCROLL LOCK meta key is latched. */ + AMETA_SCROLL_LOCK_LATCHED = 0x400000, }; /* diff --git a/native/include/android/keycodes.h b/native/include/android/keycodes.h index 496eccc..3fcf977 100644 --- a/native/include/android/keycodes.h +++ b/native/include/android/keycodes.h @@ -154,6 +154,60 @@ enum { AKEYCODE_BUTTON_START = 108, AKEYCODE_BUTTON_SELECT = 109, AKEYCODE_BUTTON_MODE = 110, + AKEYCODE_ESCAPE = 111, + AKEYCODE_FORWARD_DEL = 112, + AKEYCODE_CTRL_LEFT = 113, + AKEYCODE_CTRL_RIGHT = 114, + AKEYCODE_CAPS_LOCK = 115, + AKEYCODE_SCROLL_LOCK = 116, + AKEYCODE_META_LEFT = 117, + AKEYCODE_META_RIGHT = 118, + AKEYCODE_FUNCTION = 119, + AKEYCODE_SYSRQ = 120, + AKEYCODE_BREAK = 121, + AKEYCODE_MOVE_HOME = 122, + AKEYCODE_MOVE_END = 123, + AKEYCODE_INSERT = 124, + AKEYCODE_FORWARD = 125, + AKEYCODE_MEDIA_PLAY = 126, + AKEYCODE_MEDIA_PAUSE = 127, + AKEYCODE_MEDIA_CLOSE = 128, + AKEYCODE_MEDIA_EJECT = 129, + AKEYCODE_MEDIA_RECORD = 130, + AKEYCODE_F1 = 131, + AKEYCODE_F2 = 132, + AKEYCODE_F3 = 133, + AKEYCODE_F4 = 134, + AKEYCODE_F5 = 135, + AKEYCODE_F6 = 136, + AKEYCODE_F7 = 137, + AKEYCODE_F8 = 138, + AKEYCODE_F9 = 139, + AKEYCODE_F10 = 140, + AKEYCODE_F11 = 141, + AKEYCODE_F12 = 142, + AKEYCODE_NUM_LOCK = 143, + AKEYCODE_NUMPAD_0 = 144, + AKEYCODE_NUMPAD_1 = 145, + AKEYCODE_NUMPAD_2 = 146, + AKEYCODE_NUMPAD_3 = 147, + AKEYCODE_NUMPAD_4 = 148, + AKEYCODE_NUMPAD_5 = 149, + AKEYCODE_NUMPAD_6 = 150, + AKEYCODE_NUMPAD_7 = 151, + AKEYCODE_NUMPAD_8 = 152, + AKEYCODE_NUMPAD_9 = 153, + AKEYCODE_NUMPAD_DIVIDE = 154, + AKEYCODE_NUMPAD_MULTIPLY = 155, + AKEYCODE_NUMPAD_SUBTRACT = 156, + AKEYCODE_NUMPAD_ADD = 157, + AKEYCODE_NUMPAD_DOT = 158, + AKEYCODE_NUMPAD_COMMA = 159, + AKEYCODE_NUMPAD_ENTER = 160, + AKEYCODE_NUMPAD_EQUALS = 161, + AKEYCODE_NUMPAD_LEFT_PAREN = 162, + AKEYCODE_NUMPAD_RIGHT_PAREN = 163, + // NOTE: If you add a new keycode here you must also add it to several other files. // Refer to frameworks/base/core/java/android/view/KeyEvent.java for the full list. |