Left-hand ENTER key
(Updated: 2023-05-05 to fix some typos)
Remap “Caps Lock” key as left-hand ENTER
[ This post is relevant primarily to right-handed folks, and to left-handed folks who use a right-handed computer setup (you use the mouse with your right hand). ]
I found myself working on a one-off task that involved a fair amount of copy/paste work in my terminal emulator, building up command lines with little tidbits of data gathered from here and there, without any typing (except to hit the ENTER key to run the command).
I am using X11, so selecting the source text tidbits is
enough to “copy” it, and clicking the middle mouse button pastes it in
the target window at the location of the cursor. So far, so good. Once
the command line was ready I pressed the ENTER
key (with my right
hand), and then moved on to the next one.
I found that moving my right hand from the mouse to the ENTER
key and
then back to the mouse again was slowing me down, and the motion was
generally irritating.
It occurred to me that it would be nice if there were an ENTER
key
within reach of my left hand, and that the Caps Lock
key would be a
good candidate for remapping for that purpose.
TL;DR
To turn your Caps Lock
key into an ENTER
key, run these two commands
in a shell within your X11 session. If you are happy with the result,
then add the commands to your ~/.xsession
file (or your local system
equivalent) to have them take effect the next time you restart X
.
$ xmodmap -e 'clear Lock'
$ xmodmap -e 'keycode 66 = Return NoSymbol Return'
For best results, read the rest of the article first, though; the
Caps Lock
key on your keyboard might not be mapped to keycode 66. If
that is the case, the above will just disable your Caps Lock
key and
turn whatever key that is mapped to keycode 66 into an ENTER
key. Also
described below is an approach to preserving the mapping when keyboards
are hotplugged to the system (e.g., USB keyboards).
Background
A typical 104- or 105-key US keyboard has two ENTER
keys reachable
with your right hand:
-
one to the right side of the home row, and
-
one on the right edge of the number pad.
However, there are not any reachable from your left hand.
Since the Caps Lock
key is useless anyway, it is a good candidate to
re-map as a left-hand ENTER
key. Having that allows you to keep your
right hand on the mouse and use your left hand to press the ENTER
key,
when needed.
Gather tools and data
In order to remap the keyboard Caps Lock
key, you will need a couple
of pieces of information and two programs: xev(1)
and
xmodmap(1)
. On Debian-based systems, the
xev
program is provided by the x11-utils
package,
and the xmodmap
program is provided by the
x11-xserver-utils
package. You may have one or
both of them already, but if not:
# apt-get -u install x11-utils x11-xserver-utils
The pieces of information needed include the “keycodes” for the “Caps Lock” and “Enter” keys, as well as the mapping (to “keysyms”) in effect for the “Enter” key (so we can copy it for use with the “Caps Lock” key).
Use xev
to obtain the keycodes. Here’s what I saw initially for my “Caps Lock”
key:
KeyPress event, serial 31, synthetic NO, window 0xd400001,
root 0x1ab, subw 0x0, time 4049429559, (169,-13), root:(309,938),
state 0x10, keycode 66 (keysym 0xffe5, Caps_Lock), same_screen YES,
XLookupString gives 0 bytes:
XmbLookupString gives 0 bytes:
XFilterEvent returns: False
KeyRelease event, serial 34, synthetic NO, window 0xd400001,
root 0x1ab, subw 0x0, time 4049429670, (169,-13), root:(309,938),
state 0x12, keycode 66 (keysym 0xffe5, Caps_Lock), same_screen YES,
XLookupString gives 0 bytes:
XFilterEvent returns: False
So that tells us that our “Caps Lock” key is mapped to keycode 66. A similar query for the “Enter” key told me it was mapped to keycode 36.
Next we will use xmodmap
to obtain the keycode to keysyms mapping, and
also the current state of the Lock
modifier (from the “modifier map”).
Since we will make reference below to clearing the lock modifier, it is useful to note the initial state of it:
$ xmodmap -pm | grep '^lock'
lock Caps_Lock (0x42)
[ The -pm
option causes xmodmap
to show us the current modifier map. ]
The next thing to find out was what the xmodmap setting for the “Enter” key looked like. That was done by browsing the output of the command:
$ xmodmap -pke | less
[ The -pke
option causes xmodmap
to print on stdout
the current
keymap table, in the form of expressions that can be fed back into to
xmodmap
. ]
The two lines in that output of interest here were:
keycode 36 = Return NoSymbol Return
keycode 66 = Caps_Lock NoSymbol Caps_Lock
The first shows the setting for the “Enter” key, and the second is the initial setting for the “Caps Lock” key.
Let’s do it
To turn our “Caps Lock” key into a left-hand “Enter” key, we need to do two things:
-
Remove the lock modifier for the “Caps Lock” key.
-
Re-map the “Caps Lock” key’s keycode to the “keysyms” appropriate for an “Enter” key.
Step (1) is accomplished on the live system by using the command1:
$ xmodmap -e 'clear Lock'
Step (2) is accomplished on the live system by using the command:
$ xmodmap -e 'keycode 66 = Return NoSymbol Return'
Congratulations, your “Caps Lock” key now functions as an “Enter” key. At this point, your “Caps Lock” should have stopped having any letter case-altering effect, and should have no locking (“toggle”) effect, either. If your keyboard has an LED light that used to turn on when your “Caps Lock” key was in the lock position, you will find that the LED is no longer lit when the “Caps Lock” key is pressed (or even held down).
Make permanent
The above settings are transient as currently configured. If you were to
restart X
or reboot your machine (or something similar) the old
settings would come back when X
gets reinitialized. To have the new
settings take effect automatically in your next X
session, there are
two different approaches you might consider:
-
The first (and simpler) approach would be to add the commands exactly as typed above to your
~/.xsession
file (or local system equivalent). If your keyboard is always plugged into the machine (typical for a desktop) then that approach is good enough. -
The second, more elaborate, approach would be to take additional steps to allow the settings to take effect not only upon re-initializing
X
, but also when hotplugging the keyboard.
Make dynamic
If your keyboard is not always plugged into the machine (e.g., a USB
keyboard plugged into a laptop machine, sometimes) then you will find
that approach (1) above is not adequate. The reason is that, in X11,
those keyboard setting overrides would applied only to the devices
attached to the system at the time the settings are applied – that is,
when initializing X
.
If, for example, a USB keyboard is unplugged and then re-plugged, it will get default settings, not the override settings that we would have applied during X11 initialization.
One solution to this problem is the userspace
inputplug(1)
daemon, available in the
‘inputplug’ Debian package or from the GitHub repo
andrewshadura/inputplug. Because inputplug
monitors the system for a particular class of XInput2
events, it can determine when a new device has been (re)added to the
system. When such an event is received, it invokes a user-provided
program with the event metadata; that gives us a chance to (re)apply our
override settings.
[ The approach described below is an adaptation of the technique presented by unix.stackexchange.com user mosvy in an answer in the discussion “Prevent keyboard layout reset when USB keyboard is plugged in”. ]
This approach uses four small pieces acting on concert.
-
my-keyboard-setup
– A script with the abovexmodmap
commands in it -
on-new-kbd
– A script invoked byinputplug
; callsmy-keyboard-setup
-
~/.xsession
(1st) – Modify to callmy-keyboard-setup
(at X init time) -
~/.xsession
(2nd) – Modify to launchinputplug
daemon (at X init time)
Piece 1 of 4: my-keyboard-setup
The first is a small script that runs the xmodmap
commands we have
been using above. The reason for putting them in a dedicated script is
that it will allow us to trigger the functionality from two different
contexts.
$ mkdir -p ~/bin/
$ cat - <<EOF > ~/bin/my-keyboard-setup
> #!/bin/bash -
> xmodmap -e 'clear Lock'
> xmodmap -e 'keycode 66 = Return NoSymbol Return'
> EOF
$ chmod 0755 ~/bin/my-keyboard-setup
Piece 2 of 4: on-new-kbd
The second is a script intended to be invoked by inputplug
that will
decide when to invoke the above command (basically, only when a new
keyboard has been enabled). There is a more complete version in the
on-new-kbd Gist, but the basic idea looks like
this:
#!/bin/bash -
declare -r PROG='on-new-kbd'
# When invoked by 'inputplug', four command line parameters will be
# provided:
#
# event-type device-id device-type device-name
#
# See inputplug(1) for details.
event_type=$1
device_id=$2
device_type=$3
device_name=$4
# Examples:
# =========
#
# Note that we get two different events when we unplug the keyboard, and
# two different events when we plug the keyboard back in.
#
# Unplug events:
#
# -----------------------------------------------
# event_type: XIDeviceDisabled XIDeviceDisabled
# device_id: 10 10
# device_type: XISlaveKeyboard XISlaveKeyboard
# device_name: is_unset_or_null
# -----------------------------------------------
# event_type: XISlaveRemoved XISlaveRemoved
# device_id: 10 10
# device_type: is_unset_or_null
# device_name: is_unset_or_null
# -----------------------------------------------
#
#
# Plug event:
#
# -----------------------------------------------
# event_type: XISlaveAdded XISlaveAdded
# device_id: 10 10
# device_type: XIFloatingSlave XIFloatingSlave
# device_name: Microsoft Natural Keyboard Elite Microsoft Natural Keyboard Elite
# -----------------------------------------------
# event_type: XIDeviceEnabled XIDeviceEnabled
# device_id: 10 10
# device_type: XISlaveKeyboard XISlaveKeyboard
# device_name: Microsoft Natural Keyboard Elite Microsoft Natural Keyboard Elite
# -----------------------------------------------
case "${event_type} ${device_type}" in
'XIDeviceEnabled XISlaveKeyboard') my-keyboard-setup ;;
*)
: uninteresting event -- ignore
;;
esac
Piece 3 of 4: ~/.xession call to my-keyboard-setup
To have our keyboard mapping overrides take effect during X11
initialization, add a line such as the following to your ~/.xsession
file (or equivalent):
"${HOME}/bin/my-keyboard-setup"
Piece 4 of 4: ~/.xession run inputplug(1) daemon
Also done during X11 initialization, arrange for the inputplug
daemon
to run and to invoke the on-new-kbd
script for device add/remove and
enable/disable events. To do so, add a line such as the following to
~/.xsession
beneath the line we just added in the previous step:
/usr/bin/inputplug -c "${HOME}/bin/on-new-kbd"
Summary
At this point you should have a working left-hand ENTER
key that is
both permanent and dynamic. Enjoy!