655210e918
Left/Right-specific modifiers |
||
---|---|---|
.github | ||
example | ||
src | ||
.gitignore | ||
Cargo.lock | ||
Cargo.toml | ||
CHANGELOG.md | ||
LICENSE | ||
README.md | ||
rustfmt.toml |
𝑋𝑟𝑒𝑚𝑎𝑝 ⌨️
xremap
is a key remapper for Linux. Unlike xmodmap
, it supports app-specific remapping and Wayland.
Concept
-
Fast - Xremap is written in Rust, which is faster than JIT-less interpreters like Python.
-
Cross-platform - Xremap uses
evdev
anduinput
, which works whether you use X11 or Wayland. -
Language-agnostic - The config is JSON-compatible. Generate it from any language, e.g. Ruby, Python.
Features
- Remap any keys, e.g. Ctrl or CapsLock.
- Remap any key combination to another, even to a key sequence.
- Remap a key sequence as well. You could do something like Emacs's
C-x C-c
. - Remap a key to two different keys depending on whether it's pressed alone or held.
- Application-specific remapping. Even if it's not supported by your application, xremap can.
- Automatically remap newly connected devices by starting xremap with
--watch
. - Support Emacs-like key remapping, including the mark mode.
Prerequisite
xremap
assumes that you can use evdev
and uinput
without sudo.
You can configure it as follows:
sudo gpasswd -a YOUR_USER input
echo 'KERNEL=="uinput", GROUP="input"' | sudo tee /etc/udev/rules.d/input.rules
Then reboot your machine to make sure the udev rule is applied.
Installation
After the reboot, download a binary from Releases.
If it doesn't work, please install Rust and run one of the following commands:
# X11
cargo install xremap --features x11
# GNOME Wayland
cargo install xremap --features gnome
# Sway
cargo install xremap --features sway
# Others
cargo install xremap
You may also need to install libx11-dev
to run the xremap
binary for X11.
Usage
Write a config file directly, or generate it with xremap-ruby or xremap-python. Then run:
xremap config.yml
Dynamic binding
Xremap supports application-specific key remapping.
While Xremap uses evdev
and uinput
, which is a lower layer than X11 and Wayland,
Xremap also uses X11 or Wayland compositor-specific protocols to support application
config.
If you need this feature, make sure you use the correct binary or --features
option,
and pay attention to the error messages from xremap
.
Configuration
Your config.yml
should look like this:
modmap:
- name: Except Chrome
application:
not: Google-chrome
remap:
CapsLock: Esc
keymap:
- name: Emacs binding
application:
only: Slack
remap:
C-b: left
C-f: right
C-p: up
C-n: down
See also: example/config.yml and example/emacs.yml
modmap
modmap
is for key-to-key remapping like xmodmap.
Note that remapping a key to a modifier key, e.g. CapsLock to Control_L,
is supported only in modmap
since keymap
handles modifier keys differently.
modmap:
- name: Name # Optional
remap: # Required
KEY_XXX: KEY_YYY # Required
# or
KEY_XXX:
held: KEY_YYY # Required
alone: KEY_ZZZ # Required
alone_timeout_millis: 1000 # Optional
application: # Optional
not: [Application, ...]
# or
only: [Application, ...]
For KEY_XXX
and KEY_YYY
, use these names.
You can skip KEY_
and the name is case-insensitive. So KEY_CAPSLOCK
, CAPSLOCK
, and CapsLock
are the same thing.
Some custom aliases like SHIFT_R
, CONTROL_L
, etc. are provided.
If you specify a map containing held
and alone
, you can use the key for two purposes.
The key is considered alone
if it's pressed and released within alone_timeout_millis
(default: 1000)
before any other key is pressed. Otherwise it's considered held
.
keymap
keymap
is for remapping a sequence of key combinations to another sequence of key combinations or other actions.
keymap:
- name: Name # Optional
remap: # Required
# key press -> key press
MOD1-KEY_XXX: MOD2-KEY_YYY
# sequence (MOD1-KEY_XXX, MOD2-KEY_YYY) -> key press (MOD3-KEY_ZZZ)
MOD1-KEY_XXX:
remap:
MOD2-KEY_YYY: MOD3-KEY_ZZZ
# key press (MOD1-KEY_XXX) -> sequence (MOD2-KEY_YYY, MOD3-KEY_ZZZ)
MOD1-KEY_XXX: [MOD2-KEY_YYY, MOD3-KEY_ZZZ]
# execute a command
MOD1-KEY_XXX:
launch: ["bash", "-c", "echo hello > /tmp/test"]
# let `with_mark` also press a Shift key (useful for Emacs emulation)
MOD1-KEY_XXX: { set_mark: true } # use { set_mark: false } to disable it
# also press Shift only when { set_mark: true } is used before
MOD1-KEY_XXX: { with_mark: MOD2-KEY_YYY }
application: # Optional
not: [Application, ...]
# or
only: [Application, ...]
For KEY_XXX
, use these names.
You can skip KEY_
and the name is case-insensitive. So KEY_CAPSLOCK
, CAPSLOCK
, and CapsLock
are the same thing.
For the MOD1-
part, the following prefixes can be used (also case-insensitive):
- Shift:
SHIFT-
- Control:
C-
,CTRL-
,CONTROL-
- Alt:
M-
,ALT-
- Windows:
SUPER-
,WIN-
,WINDOWS-
You can use multiple prefixes like C-M-Shift-a
.
You may also suffix them with _L
or _R
(case-insensitive) so that
remapping is triggered only on a left or right modifier, e.g. Ctrl_L-a
.
application
application
can be used for both modmap
and keymap
, which allows you to specify application-specific remapping.
application:
not: Application
# or
not: [Application, ...]
# or
only: Application
# or
only: [Application, ...]
To check the application names, you can use the following commands:
X11
$ wmctrl -x -l
0x0280000a 0 gnome-terminal-server.Gnome-terminal ubuntu-focal Terminal
0x02600001 0 nocturn.Nocturn ubuntu-focal Nocturn
Use the name after .
in the third column (WM_CLASS
), i.e. Gnome-terminal
or Nocturn
in the above output.
GNOME Wayland
busctl --user call org.gnome.Shell /org/gnome/Shell org.gnome.Shell Eval s 'global.get_window_actors().map(a => a.get_meta_window().get_wm_class());'
Sway
swaymsg -t get_tree
Locate app_id
in the output.
License
The gem is available as open source under the terms of the MIT License.