Giving Emacs keybindings some thought

Published 2025-11-11

tag(s): #emacs

So, last weekend I finally moved away from use-package, like I predicted it would happen in an earlier post. In that post I also hinted that I was going to write about my keybinding changes...and here it is.
This post is as much self-documentation, as it is way to hopefully get some feedback and comments from others.

I had started typing a section with the history of how I got to this system, but I deleted it. The truth is that the setup I have now has some influence from what came before, but it is a complete redesign based on the the idea that commands correspond to different needs/categories.
Also, remember that I have F6 as a key right next to the spacebar, courtesy of the Dygma Raise "8-key spacebar". And F5 in the Enter key.[1]

And if you think code speaks louder than words, you can see the bindings here.
Now that I moved all of them to single file, that runs after all packages are loaded, it is very easy to detect inconsistencies or forgotten keys. The code is separated in neat pages:


6 pages in buffer bindings.el (delimiter: "^")
    28: ;; Custom prefix keymaps: editing and shortcuts (45 lines)
    73: ;; Other custom keymaps (82 lines)
   155: ;; Mode-specific bindings (28 lines)
   183: ;; Remaps (16 lines)
   199: ;; ctl-x-map (23 lines)
   222: ;; Repeat keymaps (47 lines)
    

The three types of commands

According to me, of course. According to me today, who knows what I came up with in the future.
And like with most categorizations, some commands will blur the lines between the labels.

Pure text editing: while typing

Example of these are copy-from-above-command, kill-whole-line, and hoagie-split-by-sep.
These are commands that manipulate text at the lowest level, and don't have default bindings (or are commands I wrote). I put them in their own prefix keymap, hoagie-editing-keymap. It is assigned to F6.

This makes them all accessible under my thumb[2]. Also, none of them are long sequences, just a quick key press, since they are used while typing.

Shortcuts: often used

These are things that I use often enough that I consider it worth it to have them under a key sequence. But they aren't part of the "typing flow".
It also includes keymaps that have "menu options", like the one I described for find-* commands here.

These are assigned to F5. Tapping in succession, F5 f {another letter} and I can invoke find-name-dired or find-grep-dired[3].
Other examples of commands in this group are ediff-buffers, and rgrep.

Also, as per the Emacs manual, it is suggested that users assign things in the key sequence C-C LETTER. I use these for some long-but-mnemonic sequences. For example, C-c l for Eglot:


(defvar-keymap hoagie-eglot-keymap
  :doc "Keymap for Eglot commands."
  :name "Eglot"
  "r" '("rename" . eglot-rename)
  "h" '("help"  . eldoc)
  "c" '("code actions" . eglot-code-actions))
;; "l" for LSP
(keymap-set hoagie-shortcut-keymap "l" hoagie-eglot-keymap)
    

Everything else: M-x

There are things are useful, but seldom used. For example align-regexp, or flush-lines. It is good to know about these commands, but I use them once a month (if that). I don't need to assign a key to them.
I learned from experience that if I put them under a key sequence, I will have to use the command name to find out what was the key binding anyway. So it is OK to just M-x them.

Repeat maps, too

For the longest time, I used expand-region to...well, expand the region. But after reading Mastering Emacs (specifically, the section about mark-* commands, I gave the built ins a try. And turns out that most times it is easier to use those instead.

And there's one scenario that expand-region doesn't cover: What happens if you are moving or killing or transposing two sexps or lines in a row, right next to each other? There's no "outer semantic unit" for that, and it is a pretty common scenario.
For those cases, I lean on repeat-mode:


(defvar-keymap hoagie-mark-repeat-map
  :doc "Keymap to extend selections after a mark command"
  :repeat t
  "SPC" #'mark-sexp
  "@" #'mark-word
  "h" #'mark-paragraph)
    

Another example of how I use repeat maps: some quick navigation without holding modifiers down.


(defvar-keymap hoagie-sexp-movement-repeat-map
  :doc "Keymap to repeat a few \"C-M-something\" movement commands."
  :repeat t
  "u" #'backward-up-list
  "d" #'down-list
  "f" #'forward-sexp
  "b" #'backward-sexp
  "a" #'beginning-of-defun
  "e" #'end-of-defun)
    

In closing

I think the biggest lesson related to this I've learned over my few years as an Emacser, is that if I didn't use a bound command, I should try to keep it in mind in the coming days.
But by the second time I notice I bound something and I never call it, then I can free that key.
It makes no sense to have a gazillion bindings that you don't remember, and you can M-x command-name if you need it. They don't go anywhere!

Footnotes
  1. Enter is under my left thumb :)
  2. Unless I am using the laptop on the go...
  3. I use these for multi-file replacements, via dired-do-find-regexp-and-replace and dired-do-replace-regexp-as-diff.

Share your thoughts (via email)

Back to top

Back to homepage