This page describes how to add a custom keyboard layout or option so that it will be parsed by libxkbcommon.
@attention 👋 First time hacking your keyboard layout?
@attention 📝 Read the @ref important-notes "" below before proceeding to @ref custom-config-quick-start ""!
@attention 💡 See also the @ref faq "FAQ".
@note For an introduction to XKB and keymap components, please see “@ref xkb-intro ""”.
@note For the complete XKB text format specification, see @ref keymap-text-format-v1-v2 "".
@note For distributing keyboard layouts, see @ref packaging-keyboard-layouts "".
@note The following instructions focus on a user configuration; it can be
extended to a system-wide configuration by replacing $XDG_CONFIG_HOME with
the system configuration directory in the file
locations. See @ref xkb-data-locations "" for further details.
@note Applying layout changes depends on the setup: most desktop environments propose a dedicated GUI to configure it. Please consult the corresponding configuration.
@warning The instructions of this page requires libxkbcommon as keymap compiler
and does not work in X11 sessions, because X servers have hard-coded paths.
Check your session type in the “information” or “about” screen of you desktop
environment, or execute the following command: echo $XDG_SESSION_TYPE.
@warning In particular neither setxkbmap nor xkbcomp does work in Wayland
sessions.
@important An erroneous XKB configuration may make your keyboard unusable.
Therefore it is advised to try custom configurations safely in user-space using
xkbcli tools; see “@ref testing-custom-config ""” for further details.
@tableofcontents{html:2}
This example creates a minimal custom layout that swaps the number row (numbers require Shift).
This works by defining a new [symbols] file, which tells XKB how keys map to characters.
[symbols]: @ref config-symbols-def
Create a temporary XKB directory (used later via --include):
mkdir -p "/tmp/xkb/symbols"
Create the file: /tmp/xkb/symbols/test with the following content:
default partial alphanumeric_keys
xkb_symbols "basic" {
include "us(basic)" // Use the US Qwerty layout as a base
name[Group1]= "Test (Swapped numbers)";
// Map keys <XXXX> to key symbols, ordered by their shift level
key <AE01> { [ exclam, 1] };
key <AE02> { [ at, 2] };
key <AE03> { [ numbersign, 3] };
key <AE04> { [ dollar, 4] };
key <AE05> { [ percent, 5] };
key <AE06> { [ asciicircum, 6] };
key <AE07> { [ ampersand, 7] };
key <AE08> { [ asterisk, 8] };
key <AE09> { [ parenleft, 9] };
key <AE10> { [ parenright, 0] };
};
Use the xkbcli tool provided by the libxkbcommon-tools package (or similar)
to compile and inspect the new layout:
xkbcli compile-keymap --include /tmp/xkb \
--include-defaults \
--test \
--layout test \
&& echo "valid!" || echo "invalid!"
Compilation should succeed and print “valid!”.
@note If something goes wrong, your system layout is unaffected as long as you
only use the layout with xkbcli in the /tmp directory.
To preview how keys behave interactively, use the following command. It will open a window that needs to stay focused and log the keys in the terminal. Use Esc to quit.
xkbcli compile-keymap --include /tmp/xkb \
--include-defaults \
--layout test \
| xkbcli interactive
If everything worked, you now have a working custom keyboard layout named test!
@important This step does affect your system. Ensure that the layout compiles (see the previous step) before going further. An erroneous layout may make your keyboard unusable!
$XDG_CONFIG_HOME/xkb/symbols/test –
where $XDG_CONFIG_HOME is usually $HOME/.config – so it is in the
default libxkbcommon include paths.@note If the layout is not available, try restarting your session.
This example defines a single simple layout. Read on to discover more advanced customizations:
@note It is advised to try configurations safely in user-space using a
dedicated directory that is not in the libxkbcommon default paths (e.g. not
$XDG_CONFIG_HOME); see “@ref testing-custom-config ""” for further details.
libxkbcommon searches the following paths for XKB configuration files:
| Scope | Rank | Name | Path |
|---|---|---|---|
| User | 1 | *User* configuration | @anchor user-configuration `$XDG_CONFIG_HOME/xkb/`, or `$HOME/.config/xkb/` if the `$XDG_CONFIG_HOME` environment variable is not defined. See the [XDG Base Directory Specification] for further details. |
| 2 | **Legacy** *user* configuration | @deprecated `$HOME/.xkb/` as a *legacy* alternative to the previous XDG option. | |
| System | 3 | *System*-wide configuration | @anchor system-configuration `$XKB_CONFIG_EXTRA_PATH` if set, otherwise `/xkb` – where `` is a placeholder for the system configuration directory (`/etc` on most distributions). Example: `/etc/xkb`. |
| 4 | XKB extension packages data | See @ref packaging-keyboard-layouts "". | |
| 5 | Canonical XKB root |
`$XKB_CONFIG_ROOT` if set, otherwise the data directory of the `xkeyboard-config`
(or `xkb-data`) package (denoted `` in the rest of the page):
`/xkeyboard-config-` or `/X11/xkb` on older setups.
`` is a placeholder for the package data; on most distributions this is
`/usr/share`. Example: `/usr/share/xkeyboard-config-2` and `/usr/share/X11/xkb`.
@warning Do not modify the system XKB root files, because they will be
overwritten by any update of the `xkeyboard-config` (also: `xkb-data`) package.
A keymap created with @note Where libxkbcommon runs in a privileged context (e.g. as @note The rest of the page assumes configuring a user configuration; it can
be extended to a system-wide configuration by replacing Each directory should have one or more of the following subdirectories:
The majority of user-specific configurations involve modifying [key symbols] and this is what this document focuses on. For use-cases where a user may need to add new [key types] or [compat entries] the general approach remains the same. See “@ref keymap-text-format-v1-v2 ""” for detailed descriptions for how to add those types or compat entries. You should never need to add user-specific [keycodes]. Where a keycode is missing, the addition should be filed in the upstream xkeyboard-config project. [key symbols]: @ref keysym-def [key types]: @ref key-type-def [compat entries]: @ref the-xkb_compat-section [keycodes]: @ref keycode-def How keyboard layout and options names map to keyboard data (RMLVO vs KcCGST) {#custom-config-rmlvo-kccgst}Due to how XKB is configured, there is no such thing as a “layout” in XKB
itself, or, indeed, any of the rules, models, variant, options ([RMLVO]) described
in [RMLVO]: @ref RMLVO-intro [KcCGST]: @ref KcCGST-intro For example, a common [RMLVO] configuration is layout @figure@figcaption
Output of the command:
A detailed explanation of how rules files convert [RMLVO] to [KcCGST] is out of scope for this document. See the rules file page instead. Adding a layout {#custom-layout}Adding a layout requires that the user adds [symbols] in the correct location. @sa @ref the-xkb_symbols-section "" for the full syntax
@sa @ref keycode-naming-convention "" (e.g.
[keysym]: @ref keysym-def The default rules files (usually @figure@figcaption
Content of
The The The exact details of how @remark This example uses a file name Adding an option {#custom-option}[Options][options] are sets of changes of any keymap components that affect the whole keyboard. [options]: @ref config-options-def For technical reasons, options do not have a catch-all to map option names
to files and sections and must be specifically mapped by the user. This requires
a custom rules file. As the @figure@figcaption
Content of
The This rules file maps the [RMLVO] option @important The order of the options matters in the rule file! This is due to
the sequential processing of the rules. In the example, [options-order]: @ref irrelevant-options-order The files themselves are similar to the layout examples in the previous section: @figure@figcaption
Content of
@figure@figcaption
Content of
With these in place, a user may select any layout/variant together with
the @remark This example uses file names Using system file names {#custom-config-system-file-names}The previous examples use custom keymap files with file name that do not clash
with the files in the system directory, Compatibility@attention For libxkbcommon < 1.9, the custom file must contain an
explicit default section if the system file has one, else it may break the
keyboard setup by including a section of the custom file instead of the system
one. The custom default section should enforce that the system default section
is included.
For libxkbcommon ≥ 1.9 an explicit default section is not required
anymore: libxkbcommon will look up for the proper default section in the XKB
paths:
@figure@figcaption
Content of
Overriding the system sectionsOne may override the system sections:
@warning It will affect all layouts/variants that depend on the system section. @warning Including the system section can lead to a circular import. Therefore is it highly recommended to not override the system sections and prefer creating proper independent variants. @since 1.11.0: It is possible to include the system section and avoid circular
include by prepending Discoverable layouts {#discoverable-layouts}@warning The below requires The above sections apply only to the data files and require that the user knows
about the existence of the new entries. To make custom entries discoverable by
the configuration tools (e.g. the GNOME Control Center), the new entries must
also be added to the XML file that is parsed by The following tags are required:
See the xkeyboard-config documentation for further information. The example below shows the XML file that would add the custom layout and custom options as outlined above to the XKB registry: @figure@figcaption
Content of
The default behavior of For details on the XML format, see the DTD in @note Depending on the desktop environment, it may require restarting the session in order to make the configuration changes effective. @note It is advised to try the custom configuration before restarting the
session using the various |