Skip to content

Latest commit

 

History

History
374 lines (277 loc) · 16.1 KB

README.org

File metadata and controls

374 lines (277 loc) · 16.1 KB

Ergonomic Keyboard “shajra” Mappings (with Nix)

https://github.com/shajra/shajra-keyboards/workflows/CI/badge.svg

https://img.shields.io/endpoint.svg?url=https%3A%2F%2Fgarnix.io%2Fapi%2Fbadges%2Fshajra%2Fshajra-keyboards%3Fbranch%3Dmain

About the project

This project has the “shajra” keyboard mappings for four ergonomic split keyboards:

Beyond the keymap, this project offers some streamlined automation with Nix that you can use for your own keymap. Or you can use this automation to return your keyboard to its factory default.

This automation only works for GNU/Linux (not MacOS or Windows). If you’re new to Nix, this project bundles a few guides to get you started:

The rest of this document discusses using this automation. To get the most out of the keymap itself, you may be interested in the design document explaining the motivation behind the mapping.

The mappings

The “shajra” keymaps for all four keyboards are highly similar, which works out well because the physical layouts of these keyboards are also similar. We can more easily switch from one keyboard to another and retain the design benefits of the mapping.

Model 100 and Model 01 “shajra” keymap

doc/model-100-shajra-layout.png

Ergodox EZ “shajra” keymap (Moonlander similar)

doc/ergodox-ez-shajra-layout.png

Note the Moonlander keyboard is an almost identical layout to the EZ and not illustrated here. The Moonlander has only two fewer keys on the thumb cluster. This leads to not having either Home or End on the base layer for the Moonlander (they are still in a function layer). And the “application menu” keycodes are moved to the bottom-outer corners.

Using these key mappings

This project only supports a GNU/Linux operating system (sorry, not MacOS or Windows) with the Nix package manager installed.

QMK and Kaleidoscope have build complexities and dependencies that can take a moment to work through. Nix can automate this hassle away by downloading and setting up all the necessary third-party dependencies in a way that

  • is highly reproducible
  • won’t conflict with your current system/configuration.

Using Nix, we won’t have to worry about downloading QMK or Kaleidoscope, ensuring we have the correct versions of build tools like Arduino, without messing with Git submodules or setting up environment variables. Nix does all this for us. The provided scripts simplify using Nix even further.

The following steps will get your keyboard flashed.

1. Install Nix on your GNU/Linux distribution

If you don’t have Nix installed and configured on your system, follow the instructions provided. As discussed, setting up Cachix and enabling the experimental flakes feature are both recommended.

2. Make sure your udev rules are set

To program either keyboard with a new mapping, you need to augment your OS configuration with new udev rules.

The following are recommended rules for each keyboard:

# For Ergodox EZ
ATTRS{idVendor}=="16c0", ATTRS{idProduct}=="04[789B]?", ENV{ID_MM_DEVICE_IGNORE}="1"
ATTRS{idVendor}=="16c0", ATTRS{idProduct}=="04[789A]?", ENV{MTP_NO_PROBE}="1"
SUBSYSTEMS=="usb", ATTRS{idVendor}=="16c0", ATTRS{idProduct}=="04[789ABCD]?", TAG+="uaccess"
KERNEL=="ttyACM*", ATTRS{idVendor}=="16c0", ATTRS{idProduct}=="04[789B]?", TAG+="uaccess"

# For Moonlander
SUBSYSTEMS=="usb", ATTRS{idVendor}=="0483", ATTRS{idProduct}=="df11", \
    TAG+="uaccess", SYMLINK+="stm32_dfu"

# For Model 100
SUBSYSTEMS=="usb", ATTRS{idVendor}=="3496", ATTRS{idProduct}=="0005", \
    SYMLINK+="model100", ENV{ID_MM_DEVICE_IGNORE}:="1", \
    ENV{ID_MM_CANDIDATE}:="0", MODE="0666", TAG+="uaccess", TAG+="seat"

SUBSYSTEMS=="usb", ATTRS{idVendor}=="3496", ATTRS{idProduct}=="0006", \
    SYMLINK+="model100", ENV{ID_MM_DEVICE_IGNORE}:="1", \
    ENV{ID_MM_CANDIDATE}:="0", MODE="0666", TAG+="uaccess", TAG+="seat"

# For Model 01
SUBSYSTEMS=="usb", ATTRS{idVendor}=="1209", ATTRS{idProduct}=="2300", \
    SYMLINK+="model01", ENV{ID_MM_DEVICE_IGNORE}:="1",   \
    ENV{ID_MM_CANDIDATE}:="0", MODE="0666", TAG+="uaccess", TAG+="seat"
SUBSYSTEMS=="usb", ATTRS{idVendor}=="1209", ATTRS{idProduct}=="2301", \
    SYMLINK+="model01", ENV{ID_MM_DEVICE_IGNORE}:="1",   \
    ENV{ID_MM_CANDIDATE}:="0", MODE="0666", TAG+="uaccess", TAG+="seat"

These settings should roughly correspond to the official documentation of tools and libraries used by this project:

Note, if the MODE="0666" settings above are not set, you may require root-privileges (sudo) to call the flashing scripts.

Each distribution is different, but on many GNU/Linux systems, udev rules are put in a file in /etc/udev/rules.d with a “.rules” extension.

On some systems, you can activate these rules with the following commands:

udevadm control --reload-rules udevadm trigger

Or just restart the computer.

4. For Kaleidoscope, join the necessary OS group

/NOTE:/ You don’t need this step if you’re flashing the Ergodox EZ or Moonlander.

Once udev is configured, when you plug in the Keyboardio Model 01, a serial device should appear under /dev/serial/by-id with a name matching “usb-Keyboardio_Model_01_*”. This human-readable symlink pointing to the device should be something like /dev/ttyACM0. On many systems, this device is group-owned by the “dialout” or the “uucp” group:

In the following example, we can see the device is group-owned by the “dialout” group.

ls -lL /dev/serial/by-id/usb-Keyboardio_Model_01_*
crw-rw---- 1 root dialout 166, 0 Dec 28 20:09 /dev/serial/by-id/usb-Keyboardio_Model_01_Ckbio01E-if00

On most distributions, the following commands should work to join a group (substituting $TTY_GROUP and $USERNAME):

sudo usermod -a -G $TTY_GROUP $USERNAME
newgrp $TTY_GROUP

You should see memberships in the new group with the groups command:

groups | grep dialout
users wheel video dialout docker

5. Unplug and replug your keyboard

Unplug your keyboard and plug it back in to ensure everything’s set to program. Rebooting your computer is probably overkill, but would probably work too.

6. Flash your keyboard

This project provides four scripts:

  • flash-ergodoxez
  • flash-model01
  • flash-model100
  • flash-moonlander

Calling these scripts without arguments will flash your respective keyboard with the “shajra” keymap. There is a “–factory” switch to flash your keyboard back to a factory default keymap.

If you enabled flakes in your Nix installation, you can run these scripts without installing them. Here’s an invocation illustrating doing so with flash-ergodoxez:

nix run github:shajra/shajra-keyboards#flash-ergodoxez
Flashing ZSA Technology Lab's Ergodox EZ (custom "shajra" keymap)
=================================================================

FLASH SOURCE: /nix/store/ck0bgyy2sxcmrr7jaq6kh0i70wdzwwqp-qmk-builtin-shajra-src
FLASH BINARY: /nix/store/sjx36zr53wmpa3vbkjpsjpca1kpwbb69-ergodoxez-builtin-shajra.hex

⠋ Press the reset button of your keyboard

The same works for the other three flashing scripts. Just replace “flash-ergodoxez” in the invocation above with the script of your choice.

Alternatively, the four flashing scripts are provided at the root of this project. Just clone this repository, and you can call them directly:

cd $SOME_WORKING_DIR
clone https://github.com/shajra/shajra-keyboards.git
cd shajra-keyboards
./flash-ergodoxez

Note that the first time you run the commands described below, you’ll see Nix doing a lot of downloading and compiling. After that, subsequent invocations should be quicker with less output.

Flashing an Ergodox EZ keyboard

When flashing with flash-ergodoxez, you will be prompted to press a reset button. Access this button with an unbent paperclip inserted into the small hole in the top right corner of the right keyboard half.

Flashing a Moonlander keyboard

When flashing with flash-ergodoxez, you will be prompted to press a reset button. Access this button with an unbent paperclip inserted into the small hole in the top left corner of the left keyboard half.

Flashing a Keyboardio keyboard

When flashing with flash-model100 or flash-model01, you will be prompted with instructions to hold down the Prog key, and then press Enter.

The Prog key is hardwired to be the top-left-most key of the Keyboardio Model 01, but the Enter key can be remapped. If you forget where the Enter has been mapped to on your Keyboard, you can hit Enter on another connected keyboard.

Reverting to the factory default mapping

This project’s scripts won’t save off your previous keymap from your keyboard. But we can revert to the OEM keymap that your keyboard shipped with.

Reverting to the OEM keymap can be done with the -F / --factory switch, which all the flashing scripts support. If you forget your options, these scripts have a -h / --help switch.

Customization

Customizing keymaps

The provided code is relatively compact. In the keymaps directory, you should find familiar files you would edit in QMK or Kaleidoscope projects, respectively. These keymaps are compiled into the flashing scripts provided with this project.

For both keyboards, The “shajra” keymap is in its own directory. You can make your own keymaps and put them in a sibling directory with the name of your choice, and they’ll be compiled in as well.

If you don’t want to use keymaps compiled into the flashing scripts, you can use another directory of keymaps at runtime with the -K / -keymaps switch.

Then you can use the -k / --keymap switch to load your custom keymap by the name you chose for the keymap in the “keymaps” directory. The scripts should pick up changes, rebuild anything necessary, and flash your keyboard.

The used keymap source code is copied into /nix/store, and the invocation of the flashing scripts will print out a “FLASH SOURCE:” line indicating the source used for compiling/flashing for your reference. These are the whole source trees you’d typically use if following the QMK or Kaleidoscope documentation manually.

Development

This project relies heavily on Nix, primarily to help deal with all the complexity of setting up dependencies. The development of this project also relies on an experimental feature of Nix called flakes, not required to use the project. See the included introduction to Nix if you’re new to Nix or flakes.

If you want to check that everything builds before flashing your keyboard, you can build locally everything built by this project’s continuous integration:

tree $(nix build --no-link --print-out-paths) 2>/dev/null
/nix/store/vg02qk57pwfsv5i4kp4vjcwvcman2lp2-shajra-keyboards-ci
├── build-ergodoxez-builtin-shajra-flash -> /nix/store/h1mjg5g8sdpgb30qhbn2078d4fr316gs-ergodoxez-builtin-shajra-flash
├── build-ergodoxez-builtin-shajra-hex -> /nix/store/sjx36zr53wmpa3vbkjpsjpca1kpwbb69-ergodoxez-builtin-shajra.hex
├── build-ergodoxez-factory-flash -> /nix/store/km7qzwz5lw2w60afvxhn9jfcva9c0vrn-ergodoxez-factory-flash
├── build-ergodoxez-factory-hex -> /nix/store/4gv794n3di2b97s8pai1zqfcfrkmvlgw-ergodoxez-factory.hex
├── build-model01-builtin-shajra-flash -> /nix/store/i9sdqlzf13ax32rvml4dzk3rgjb4rr4b-model01-builtin-shajra-flash
├── build-model01-builtin-shajra-hex -> /nix/store/jani7937ypra4iwfgh2qfw7cbpr05hsn-model01-builtin-shajra-hex
├── build-model01-factory-flash -> /nix/store/z1p0ahl7hdxpgdb9gw5caphrvb8f7cdi-model01-factory-flash
├── build-model01-factory-hex -> /nix/store/lwiq5zrpp147818q5w8v117bx3adplzi-model01-factory-hex
├── build-model100-builtin-shajra-flash -> /nix/store/g71ya9g96bfxj96knvwkgc2viblfvgj1-model100-builtin-shajra-flash
├── build-model100-builtin-shajra-hex -> /nix/store/9psl103fyis93dnyfgqjncyzjy1c5p15-model100-builtin-shajra-hex
├── build-model100-factory-flash -> /nix/store/g4w2j8aqq7x983faiwb2qhqlpz15h8v6-model100-factory-flash
├── build-model100-factory-hex -> /nix/store/mrrn2jh9lx705sasdr1i2w3cs8wj8ldm-model100-factory-hex
├── build-moonlander-builtin-shajra-flash -> /nix/store/cshald5p88brphz71p2a1sdiz6vqflxb-moonlander-builtin-shajra-flash
├── build-moonlander-builtin-shajra-hex -> /nix/store/vqbddf5n0ps7by6sidj5v1qc5q846l41-moonlander-builtin-shajra.bin
├── build-moonlander-factory-flash -> /nix/store/v9zgy775r0802lzhw67yfa30pp1nzabv-moonlander-factory-flash
├── build-moonlander-factory-hex -> /nix/store/bjhmdk016xclqhravzb21bpjxpbnpgbf-moonlander-factory.bin
├── flash-ergodoxez -> /nix/store/c3rs3yvmbg7bz5jzb1f6rcy8myz6by4k-flash-ergodoxez
├── flash-model01 -> /nix/store/ws8qm3avl7w0sgp5nn9qax7v3hcd193p-flash-model01
├── flash-model100 -> /nix/store/k1k206wf20i3n0pq71dqs9dbyvs85cap-flash-model100
├── flash-moonlander -> /nix/store/apcda7mwsrklgvrfz1xfniwci4lsr0pa-flash-moonlander
└── licenses -> /nix/store/3rpjxncsgvnvhzdp83shabzn8b3bsrq2-shajra-keyboards-licenses

18 directories, 4 files

Release

The “main” branch of the GitHub repository has the latest version of this code. There is currently no commitment to either forward or backward compatibility. However, the scripts for compiling/flashing are considered stable and less likely to change than the “shajra” keymap.

“user/shajra” branches are personal branches that may be force-pushed to. The “main” branch should not experience force-pushes and is recommended for general use.

License

This project is not a modified work in the traditional sense. It provides scripts the end user runs to make a modified work. Most of the source code modified (QMK, Kaleidoscope, and Model 01) is licensed under either GPLv2 or GPLv3.

If you have Nix installed, then a provided script licenses-thirdparty can be run to download all original source used, including license information.

In the spirit of the projects we build upon, all files in this “shajra-keyboards” project are licensed under the terms of GPLv3 or (at your option) any later version.

Please see the COPYING.md file for more details.

Contribution

Feel free to file issues and submit pull requests with GitHub. Ideas for how to improve automation are welcome. If you have ideas on how to improve the “shajra” keymap, just make a compelling argument considering the factors that have already gone into its design.

There is only one author to date, so the following copyright covers all files in this project:

Copyright © 2019 Sukant Hajra