1

I created a custom Android keyboard with keys for hexadecimal numbers (0..9, A..F). It does not have a Shift/CapsLock key. The custom keyboard's layout is defined in an .xml file like this:

<Keyboard xmlns:android="http://schemas.android.com/apk/res/android"
    android:keyWidth="33%p" android:horizontalGap="0px" android:verticalGap="0px" android:keyHeight="50dip">
  <Row>
    <Key android:codes="7" android:keyLabel="0" android:keyEdgeFlags="left" />
    <Key android:codes="8" android:keyLabel="1" />
    <Key android:codes="9" android:keyLabel="2" />
    <Key android:codes="10" android:keyLabel="3" />
    <Key android:codes="11" android:keyLabel="4" android:keyEdgeFlags="right" />
  </Row>
  <Row>    
    <Key android:codes="12" android:keyLabel="5" android:keyEdgeFlags="left" />
    <Key android:codes="13" android:keyLabel="6" />
    <Key android:codes="14" android:keyLabel="7" />
    <Key android:codes="15" android:keyLabel="8" />
    <Key android:codes="16" android:keyLabel="9" android:keyEdgeFlags="right" />
  </Row>
  <Row>
    <Key android:codes="29" android:keyLabel="A" android:keyEdgeFlags="left" />
    <Key android:codes="30" android:keyLabel="B" />
    <Key android:codes="31" android:keyLabel="C" />
    <Key android:codes="32" android:keyLabel="D" />
    <Key android:codes="33" android:keyLabel="E" android:keyEdgeFlags="right" />
  </Row>
  <Row>
    <Key android:codes="67" android:keyIcon="@drawable/sym_keyboard_delete" android:iconPreview="@drawable/sym_keyboard_delete" android:keyEdgeFlags="left" />
    <Key android:codes="34" android:keyLabel="F" />
    <Key android:codes="66" android:keyEdgeFlags="right" android:keyIcon="@drawable/sym_keyboard_feedback_return" android:iconPreview="@drawable/sym_keyboard_feedback_return" />
  </Row>
</Keyboard>

The custom keyboard works fine, my only problem is that the keys 'A' to 'F' actually generate lower-case chars, and I'd like them to be shifted to upper-cases.

My custom keyboard's Key event handler is like this:

mHexKeyboardView.Key += (sender, e) => {
    long eventTime = JavaSystem.CurrentTimeMillis();

    // Create a new key event
    // KeyEvent(long downTime, long eventTime, int action, int code, int repeat, int metaState, int deviceId, int scancode, int flags)
    KeyEvent ev = new KeyEvent(eventTime, eventTime, KeyEventActions.Down, e.PrimaryCode, 0, 0, 0, 0, KeyEventFlags.SoftKeyboard | KeyEventFlags.KeepTouchMode);

    this.DispatchKeyEvent(ev);
};

And I'd like to force a "conversion" to upper-case in the Key event handler (not anywhere else). For example when key 'A' is pressed, e.PrimaryCode = Android.Views.Keycode.A, and my EditView shall receive char 'A' and not 'a'.

I guess that I should provide some 'metaState' value to the KeyEvent() constructor and have the key 'shifted', maybe?

Any suggestions/examples on this topic?

Thanks!

GigelPopescu
  • 31
  • 1
  • 5

1 Answers1

0

You need to indicate you want the value shifted using a MetaState of MetaKeyStates.ShiftLeftOn as the 6th parameter in the KeyEvent constructor. But you need to do this only for the letters (A to B) for the numbers you need to keep sending 0.

For that you can create something like:

var shiftedArray = new [] { "A", "B", "C", "D", "E", "F"};

mKeyboardView.Key += (sender, e) => {
    long eventTime = JavaSystem.CurrentTimeMillis();

    var isShifted = shiftedArray.Any (a => a == e.PrimaryCode.ToString());

    MetaKeyStates metaKeyState = isShifted ? MetaKeyStates.ShiftLeftOn : 0;

    KeyEvent ev = new KeyEvent(eventTime, eventTime, KeyEventActions.Down, e.PrimaryCode, 0, metaKeyState , 0, 0, KeyEventFlags.SoftKeyboard | KeyEventFlags.KeepTouchMode);

    this.DispatchKeyEvent(ev);
};

Any value you enter in the shiftedArray will be shifted. You can replace this with IFs, switch/case or any other algorithm you find more suitable for you, did it like this for simplicity.

Hope this helps!

pinedax
  • 9,246
  • 2
  • 23
  • 30