• You are not logged in.

    Colemak for external keyboards in Android

    • Started by f8l
    • 3 Replies:
    • Reputation: 2
    • From: Poznań, Poland
    • Registered: 16-Feb-2014
    • Posts: 5

    (A followup to Android External Keyboard & Colemak?)

    Recently I got an Android tablet as a gift, and, naturally,
    I wanted to be able to type on it normally. Since I don't
    belong to the elite group of multi-layout typists,
    I had to find a way to teach my device what Colemak is.
    Below is what I had to do to remap keys on my 4.0 powered tablet.
    I hope this helps other Colemak users to type as they want.

    Most information I needed can be found here:
    https://source.android.com/devices/tech … files.html

    I'll use the word „keymap” instead of „key character map file”.

    You'll need a way to create some directories and files in /data,
    so you may need adb (for devices which are not marked
    as production models) or root privileges. Other methods of putting
    a file to your device, such as a recovery script, should also work.

    1. Get your keyboard's VID and PID.

      Keymaps in Android are device specific. This means you have to repeat
      this tutorial for each keyboard you intend to use. Alternatively, you can
      edit the default keymap, but that's not advised. If you have multiple
      keyboards and you know what you're doing, change the default keymap
      in /system/usr/keychars/Generic.kcm and skip this step.

      Below are instructions on how to get the IDs on Linux systems (Android inclusive).
      It may also work on other Unix-likes, such as the BSD family.
      On NetBSD, you may want to use ‘usbdevs -v’ instead of ‘lsusb’ in this step.
      Windows users may use a device manager, or their Android device directly.

      1. Open a terminal emulator (you may need to install one first) and run `lsusb`.

        Sample output from my tablet:

        Bus 001 Device 001: ID 1d6b:0002
        Bus 002 Device 001: ID 1d6b:0002
        Bus 003 Device 001: ID 1d6b:0001
      2. Connect your keyboard.

      3. Rerun `lsusb` and remember the IDs of device which appeared
        compared to the output in step 1.a.

        In my case:

        Bus 001 Device 001: ID 1d6b:0002
        Bus 002 Device 001: ID 1d6b:0002
        Bus 003 Device 001: ID 1d6b:0001
        Bus 001 Device 002: ID 0a81:0205

        … 0a81 is the VID and 0205 is the PID I'm looking for.
        In fact these are IDs of a cheap PS/2 → USB adapter
        which came with my TypeMatrix2020.
        You can save these IDs for convenience:

        VID=«your vid»; PID=«your pid»
    2. Download http://f8l.netne.net/Colemak_pl.kcm or copy from post below.

    3. Season to taste.
      The file I provide is not a complete Colemak keymap.
      Since Android doesn't support all the accent dead keys
      Colemak does, it is impossible to get a full Colemak layout.
      For now I've made a Polish version of Colemak with my personal
      adjustments (AltGr+Shift+. → …, « and ‹ are swapped,
      ‚ and „ under the 9 key etc.),
      so if you need other diacritical characters, you'll need to
      edit the file according to the site I mentioned above.

    4. Rename the file to Vendor_«VID»_Product_«PID».kcm
      If you have saved you IDs earlier in step 1.c, you can just:

      mv Colemak_pl.kcm Vendor_$VID_Product_$PID.kcm

      In my case, the proper name is „Vendor_0a81_Product_0205.kcm”.
      Note that the hexadecimal letters should be lowercase
      (at least that's what worked for me).
      From now on, I'll shortcut the name of the file as Vendor_(…).kcm

    5. Put the file into /data/system/devices/keychars/
      You can also put it into /system/usr/keychars/, but this
      requires remounting your /system partition for writing.
      You have to put the file into the /system partition
      if your system already has a keymap for your keyboard.

      There are several methods of placing the file in proper directory.

      1. Using adb.
        Connect your Android device to a computer with adb and execute:

        adb root
        adb shell mkdir -p /data/system/devices/
        adb push Vendor_(…).kcm /data/system/devices/keychars/

        This only works on devices not marked as production models.
        If the first command errors out, you'll have to use another method.
        If the second command errors out due to mkdir without -p support,
        try to split it like this:

        adb shell 'mkdir /data/system; mkdir /data/system/devices'

        … and proceed with the third command.

      2. Using root privileges.
        If your device has been rooted, the task is as easy as:

        su
        mkdir -p /data/system/devices/
        mv Vendor_(…).kcm /data/system/devices/keychars/

        Like in the method above, you can split the second command if it fails.
        There are some catches though. If the mv command fails, try to use cp instead.
        If you don't have cp, cat is your best friend:

        cat Vendor_(…).kcm > /data/system/devices/keychars/Vendor_(…).kcm

        I don't know if there exist Android devices without cat,
        but in case you own one, you'll have to get busybox,
        or use some other hackish way of copying files.

      3. Using recovery script
        I'll not cover it in detail now, but it involves preparing a
        special update.zip file, and booting the device in recovery mode.
        This method works for old devices with recovery software
        which doesn't require the update.zip file to be signed.
        There are other ways, like flashing a custom /recovery
        partitions, but this is quite invasive and you need to know
        what you are doing, so you're on your own.

    6. Re-plug your keyboard.

    7. Enjoy.
      In case you frown at this point, you may want to launch logcat
      to see what's wrong.

      1. Unplug your keyboard.

      2. Launch logcat.

      3. Plug your keyboard in.

      4. Wait a moment.

      5. Terminate logcat or freeze your terminal.

      6. Read the output of logcat.

      7. Use your head or call for help.

    Changelog:
    07-May-2016 19:30 Added a hint about usbdevs
    07-May-2016 19:15:09 Reworded sentence with a typo in 5b (‘If your have rooted your device’) and added this changelog
    17-Jan-2015 22:23:27 Mentioned the post with .kcm file included
    16-Feb-2014 20:07:19 Initial version

    What do you think about a public repository with custom .kcm files
    for various language variants of Colemak?

    Last edited by f8l (07-May-2016 19:30:16)
    Offline
    • 1
    • Reputation: 2
    • From: Poznań, Poland
    • Registered: 16-Feb-2014
    • Posts: 5

    Attaching the .kcm file to make this more self-contained.
    My hosting went down and I forgot to re-upload the file earlier.
    It's going to be much safer here. ;-)

    #
    # Polish variant of Colemak for qwerty keyboards
    #
    
    type FULL
    
    ### Basic QWERTY keys ###
    
    key A {
        label:                              'A'
        base:                               'a'
        shift, capslock:                    'A'
        ctrl, alt, meta:                    none
        ralt:        '\u0105'
    # LATIN SMALL LETTER A WITH OGONEK
        shift+ralt:    '\u0104'
    # LATIN CAPITAL LETTER A WITH OGONEK
    }
    
    key B {
        label:                              'B'
        base:                               'b'
        shift, capslock:                    'B'
        ctrl, alt, meta:                    none
    }
    
    key C {
        label:                              'C'
        base:                               'c'
        shift, capslock:                    'C'
        alt:                                '\u00e7'
        shift+alt:                          '\u00c7'
        ctrl, meta:                         none
        ralt:        '\u0107'
    # LATIN SMALL LETTER C WITH OGONEK
        shift+ralt:    '\u0106'
    # LATIN CAPITAL LETTER C WITH OGONEK
    }
    
    key D {
        label:                              'D'
        base:                               's'
        shift, capslock:                    'S'
        ctrl, alt, meta:                    none
        ralt:        '\u015B'
    # LATIN SMALL LETTER S WITH ACUTE
        shift+ralt:    '\u015A'
    # LATIN CAPITAL LETTER S WITH OGONEK
    }
    
    key E {
        label:                              'E'
        base:                               'f'
        shift, capslock:                    'F'
        alt:                                '\u0301'
        ctrl, meta:                         none
    }
    
    key F {
        label:                              'F'
        base:                               't'
        shift, capslock:                    'T'
        ctrl, alt, meta:                    none
    }
    
    key G {
        label:                              'G'
        base:                               'd'
        shift, capslock:                    'D'
        ctrl, alt, meta:                    none
    }
    
    key H {
        label:                              'H'
        base:                               'h'
        shift, capslock:                    'H'
        ctrl, alt, meta:                    none
    }
    
    key I {
        label:                              'I'
        base:                               'u'
        shift, capslock:                    'U'
        alt:                                '\u0302'
        ctrl, meta:                         none
    }
    
    key J {
        label:                              'J'
        base:                               'n'
        shift, capslock:                    'N'
        ctrl, alt, meta:                    none
        ralt:        '\u0144'
    # LATIN SMALL LETTER N WITH ACUTE
        shift+ralt:    '\u0145'
    # LATIN CAPITAL LETTER N WITH ACUTE
    }
    
    key K {
        label:                              'K'
        base:                               'e'
        shift, capslock:                    'E'
        ctrl, alt, meta:                    none
        ralt:        '\u0119'
    # LATIN SMALL LETTER E WITH OGONEK
        shift+ralt:    '\u0118'
    # LATIN CAPITAL LETTER E WITH OGONEK
    }
    
    key L {
        label:                              'L'
        base:                               'i'
        shift, capslock:                    'I'
        ctrl, alt, meta:                    none
    }
    
    key M {
        label:                              'M'
        base:                               'm'
        shift, capslock:                    'M'
        ctrl, alt, meta:                    none
    }
    
    key N {
        label:                              'N'
        base:                               'k'
        shift, capslock:                    'K'
        alt:                                '\u0303'
        ctrl, meta:                         none
    }
    
    key O {
        label:                              'O'
        base:                               'y'
        shift, capslock:                    'Y'
        ctrl, alt, meta:                    none
    }
    
    key P {
        label:                              'P'
        base:                               ';'
        shift, capslock:                    ':'
        ctrl, alt, meta:                    none
    }
    
    key Q {
        label:                              'Q'
        base:                               'q'
        shift, capslock:                    'Q'
        ctrl, alt, meta:                    none
    }
    
    key R {
        label:                              'R'
        base:                               'p'
        shift, capslock:                    'P'
        ctrl, alt, meta:                    none
    }
    
    key S {
        label:                              'S'
        base:                               'r'
        shift, capslock:                    'R'
        alt:                                '\u00df'
        ctrl, meta:                         none
    }
    
    key T {
        label:                              'T'
        base:                               'g'
        shift, capslock:                    'G'
        ctrl, alt, meta:                    none
    }
    
    key U {
        label:                              'U'
        base:                               'l'
        shift, capslock:                    'L'
        alt:                                '\u0308'
        ctrl, meta:                         none
        ralt:        '\u0142'
    # LATIN SMALL LETTER L WITH STROKE
        shift+ralt:    '\u0141'
    # LATIN CAPITAL LETTER L WITH STROKE
    }
    
    key V {
        label:                              'V'
        base:                               'v'
        shift, capslock:                    'V'
        ctrl, alt, meta:                    none
    }
    
    key W {
        label:                              'W'
        base:                               'w'
        shift, capslock:                    'W'
        ctrl, alt, meta:                    none
    }
    
    key X {
        label:                              'X'
        base:                               'x'
        shift, capslock:                    'X'
        ctrl, alt, meta:                    none
        ralt:        '\u017A'
    # LATIN SMALL LETTER Z WITH ACUTE
        shift+ralt:    '\u0179'
    # LATIN CAPITAL LETTER Z WITH ACUTE
    }
    
    key Y {
        label:                              'Y'
        base:                               'j'
        shift, capslock:                    'J'
        ctrl, alt, meta:                    none
    }
    
    key Z {
        label:                              'Z'
        base:                               'z'
        shift, capslock:                    'Z'
        ctrl, alt, meta:                    none
        ralt:        '\u017C'
    # LATIN SMALL LETTER Z WITH DOT ABOVE
        shift+ralt:    '\u017B'
    # LATIN CAPITAL LETTER Z WITH DOT ABOVE
    }
    
    key 0 {
        label, number:                      '0'
        base:                               '0'
        shift:                              ')'
        ctrl, alt, meta:                    none
        ralt:        '\u2019'
    # RIGHT SINGLE QUOTATION MARK
        shift+ralt:    '\u201D'
    # RIGHT DOUBLE QUOTATION MARK
    }
    
    key 1 {
        label, number:                      '1'
        base:                               '1'
        shift:                              '!'
        ctrl, alt, meta:                    none
    }
    
    key 2 {
        label, number:                      '2'
        base:                               '2'
        shift:                              '@'
        ctrl, alt, meta:                    none
    }
    
    key 3 {
        label, number:                      '3'
        base:                               '3'
        shift:                              '#'
        ctrl, alt, meta:                    none
    }
    
    key 4 {
        label, number:                      '4'
        base:                               '4'
        shift:                              '$'
        ctrl, alt, meta:                    none
    }
    
    key 5 {
        label, number:                      '5'
        base:                               '5'
        shift:                              '%'
        ctrl, alt, meta:                    none
    }
    
    key 6 {
        label, number:                      '6'
        base:                               '6'
        shift:                              '^'
        ctrl, alt, meta:                    none
        alt+shift:                          '\u0302'
    }
    
    key 7 {
        label, number:                      '7'
        base:                               '7'
        shift:                              '&'
        ctrl, alt, meta:                    none
    }
    
    key 8 {
        label, number:                      '8'
        base:                               '8'
        shift:                              '*'
        ctrl, alt, meta:                    none
        ralt:        '\u00FE'
    # LATIN SMALL LETTER THORN
        shift+ralt:    '\u00DE'
    # LATIN CAPITAL LETTER THORN
    }
    
    key 9 {
        label, number:                      '9'
        base:                               '9'
        shift:                              '('
        ctrl, alt, meta:                    none
        ralt:        '\u201A'
    # SINGLE LOW-9 QUOTATION MARK
        shift+ralt:    '\u201E'
    # DOUBLE LOW-9 QUOTATION MARK
    }
    
    key SPACE {
        label:                              ' '
        base:                               ' '
        ctrl:                               none
        alt, meta:                          fallback SEARCH
    }
    
    key ENTER {
        label:                              '\n'
        base:                               '\n'
        ctrl, alt, meta:                    none
    }
    
    key TAB {
        label:                              '\t'
        base:                               '\t'
        ctrl, alt, meta:                    none
    }
    
    key COMMA {
        label, number:                      ','
        base:                               ','
        shift:                              '<'
        ctrl, alt, meta:                    none
    }
    
    key PERIOD {
        label, number:                      '.'
        base:                               '.'
        shift:                              '>'
        ctrl, alt, meta:                    none
        shift+ralt:    '\u2026'
    # HORIZONTAL ELLIPSIS
    }
    
    key SLASH {
        label, number:                      '/'
        base:                               '/'
        shift:                              '?'
        ctrl, alt, meta:                    none
    }
    
    key GRAVE {
        label, number:                      '`'
        base:                               '`'
        shift:                              '~'
        alt:                                '\u0300'
        alt+shift:                          '\u0303'
        ctrl, meta:                         none
    }
    
    key MINUS {
        label, number:                      '-'
        base:                               '-'
        shift:                              '_'
        ctrl, alt, meta:                    none
        ralt:        '\u2013'
    # EN DASH
        shift+ralt:    '\u2014'
    # EM DASH
    }
    
    key EQUALS {
        label, number:                      '='
        base:                               '='
        shift:                              '+'
        ctrl, alt, meta:                    none
    }
    
    key LEFT_BRACKET {
        label, number:                      '['
        base:                               '['
        shift:                              '{'
        ctrl, alt, meta:                    none
        ralt:        '\u2039'
    # SINGLE LEFT-POINTING ANGLE QUOTATION MARK
        shift+ralt:    '\u00AB'
    # LEFT-POINTING DOUBLE ANGLE QUOTATION MARK
    }
    
    key RIGHT_BRACKET {
        label, number:                      ']'
        base:                               ']'
        shift:                              '}'
        ctrl, alt, meta:                    none
        ralt:        '\u203A'
    # SINGLE RIGHT-POINTING ANGLE QUOTATION MARK
        shift+ralt:    '\u00BB'
    # RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK
    }
    
    key BACKSLASH {
        label, number:                      '\\'
        base:                               '\\'
        shift:                              '|'
        ctrl, alt, meta:                    none
    }
    
    key SEMICOLON {
        label, number:                      ';'
        base:                               'o'
        shift:                              'O'
        ctrl, alt, meta:                    none
        ralt:        '\u00F3'
    # LATIN SMALL LETTER O WITH ACUTE
        shift+ralt:    '\u00D3'
    # LATIN CAPITAL LETTER O WITH ACUTE
    }
    
    key APOSTROPHE {
        label, number:                      '\''
        base:                               '\''
        shift:                              '"'
        ctrl, alt, meta:                    none
    }
    
    ### Numeric keypad ###
    
    key NUMPAD_0 {
        label, number:                      '0'
        base:                               fallback INSERT
        numlock:                            '0'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_1 {
        label, number:                      '1'
        base:                               fallback MOVE_END
        numlock:                            '1'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_2 {
        label, number:                      '2'
        base:                               fallback DPAD_DOWN
        numlock:                            '2'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_3 {
        label, number:                      '3'
        base:                               fallback PAGE_DOWN
        numlock:                            '3'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_4 {
        label, number:                      '4'
        base:                               fallback DPAD_LEFT
        numlock:                            '4'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_5 {
        label, number:                      '5'
        base:                               fallback DPAD_CENTER
        numlock:                            '5'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_6 {
        label, number:                      '6'
        base:                               fallback DPAD_RIGHT
        numlock:                            '6'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_7 {
        label, number:                      '7'
        base:                               fallback MOVE_HOME
        numlock:                            '7'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_8 {
        label, number:                      '8'
        base:                               fallback DPAD_UP
        numlock:                            '8'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_9 {
        label, number:                      '9'
        base:                               fallback PAGE_UP
        numlock:                            '9'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_LEFT_PAREN {
        label, number:                      '('
        base:                               '('
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_RIGHT_PAREN {
        label, number:                      ')'
        base:                               ')'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_DIVIDE {
        label, number:                      '/'
        base:                               '/'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_MULTIPLY {
        label, number:                      '*'
        base:                               '*'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_SUBTRACT {
        label, number:                      '-'
        base:                               '-'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_ADD {
        label, number:                      '+'
        base:                               '+'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_DOT {
        label, number:                      '.'
        base:                               fallback FORWARD_DEL
        numlock:                            '.'
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_COMMA {
        label, number:                      ','
        base:                               ','
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_EQUALS {
        label, number:                      '='
        base:                               '='
        ctrl, alt, meta:                    none
    }
    
    key NUMPAD_ENTER {
        label:                              '\n'
        base:                               '\n' fallback ENTER
        ctrl, alt, meta:                    none fallback ENTER
    }
    
    ### Special keys on phones ###
    
    key AT {
        label, number:                      '@'
        base:                               '@'
    }
    
    key STAR {
        label, number:                      '*'
        base:                               '*'
    }
    
    key POUND {
        label, number:                      '#'
        base:                               '#'
    }
    
    key PLUS {
        label, number:                      '+'
        base:                               '+'
    }
    
    ### Non-printing keys ###
    
    key ESCAPE {
        base:                               fallback BACK
        alt, meta:                          fallback HOME
        ctrl:                               fallback MENU
    }
    
    ### Gamepad buttons ###
    
    key BUTTON_A {
        base:                               fallback BACK
    }
    
    key BUTTON_B {
        base:                               fallback BACK
    }
    
    key BUTTON_C {
        base:                               fallback BACK
    }
    
    key BUTTON_X {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_Y {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_Z {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_L1 {
        base:                               none
    }
    
    key BUTTON_R1 {
        base:                               none
    }
    
    key BUTTON_L2 {
        base:                               none
    }
    
    key BUTTON_R2 {
        base:                               none
    }
    
    key BUTTON_THUMBL {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_THUMBR {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_START {
        base:                               fallback HOME
    }
    
    key BUTTON_SELECT {
        base:                               fallback MENU
    }
    
    key BUTTON_MODE {
        base:                               fallback MENU
    }
    
    key BUTTON_1 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_2 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_3 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_4 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_5 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_6 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_7 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_8 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_9 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_10 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_11 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_12 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_13 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_14 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_15 {
        base:                               fallback DPAD_CENTER
    }
    
    key BUTTON_16 {
        base:                               fallback DPAD_CENTER
    }
    Offline
    • 1
    • Reputation: 0
    • Registered: 29-Dec-2010
    • Posts: 30

    Hi.

    Has anyone tried this out yet?

    @ f81  - You have done a fabulous job on this.  But, I have to admit, I am a little daunted by it.

    Any tips on integrating this into my Google Next Android reader?

    Offline
    • 0
    • Reputation: 2
    • From: Poznań, Poland
    • Registered: 16-Feb-2014
    • Posts: 5

    Well… I did. ;-)
    Also, there was at least one person on #colemak channel who asked about Colemak on Android recently,
    which prompted me to revisit this topic and find that it has been replied to.
    Thank you for praising my guide, but can you try not to misspell my nickname, please?

    I can’t help you until you tell me something more specific about your problem.
    If ‘it’ in your ‘I am a little daunted by it’ refers to the whole guide,
    I’m sorry, but I tried to be as specific as I could.
    If you could narrow ‘it’ down to a specific step/substep/sentence,
    I could try to elaborate, but I can’t promise anything.

    Also, I can’t promise this guide will work with newer versions of Android or on devices different than mine.
    I’m not even sure this guide is still relevant – maybe Colemak has been alraedy adopted by Android?

    Offline
    • 0