Loading...
Searching...
No Matches
XKB Compatibility

This page presents the differences between the XKB 1.0 specification implemented in current X servers and its implementation in libxkbcommon.

xkbcommon has removed support for some parts of the specification which introduced unnecessary complications. Many of these removals were in fact not implemented, or half-implemented at best, as well as being totally unused in the standard keyboard layout database, xkeyboard-config.

On the other hand, xkbcommon has notable additions that lift hard-coded limitation of the X11 Protocol.

Todo
  This page is work in progress. It aims to be exhaustive. Please report any issue.

# Keymap support

## General features

Keymap features compatibility table
Feature | X11 | xkbcommon (v1 format) | xkbcommon (v2 format)
--- | --- | --- | ---
Wayland support | ❌️ No support Wayland support requires the XWayland compatibility layer. | ✅ Full support libxkbcommon is the reference implementation of the keyboard keymap handling (parsing/serializing, state) for Wayland.
User configuration | ❌️ No support Layout database path is hard-coded in xserver. xkbcomp enables path configuration, but setxkbmap support is incomplete. | ✅ Full support Multiple layout database paths can be used simultaneously, enabling user-space configuration. See User-configuration for further information.

Configuration via third-party packages

❌️ No support

Layout database path is hard-coded in xserver.

xkbcomp enables path configuration, but setxkbmap support is incomplete.

✅ Full support (since 1.13)

Multiple layout database paths can be used simultaneously, enabling third-party packages to extend the base configuration without hacking its files.

See Packaging keyboard layouts for further information.

Keycode override with aliases | ❌️ No support Keycodes have always priority over aliases. | ✅ Full support (since 1.12) Keycodes and aliases share the same namespace.
Extended keycodes | ❌️ No support Limited to 8-bit keycodes. | ✅ Full support Support all Linux keycodes using 32-bit keycodes.
Extended key names | ❌️ No support Limited to 4-character names. | ✅ Full support Support any key names of any length.
Extended number of layouts | ❌️ No support Limited to 4 layouts. | ❌️ No support Limited to 4 layouts. | ✅ Full support (since 1.11) Enable up to 32 layouts when using XKB_KEYMAP_FORMAT_TEXT_V2.
Unified modifiers | ❌️ No support Clear separation between real (i.e. core) and virtual modifiers. | ✅ Full support Real and virtual modifiers have been collapsed into the same namespace, with a “significant” flag that largely parallels the core/virtual split. Real modifiers are predefined modifiers with fixed encoding and considered merely as a X11 compatibility feature.
Extended modifiers | ❌️ No support Limited to up to 8 independent modifiers. | ✅ Full support Enable up to 32 independent modifiers.

Canonical virtual modifiers

❌️ No support

Virtual modifiers can only mapped to real modifiers (8 bits).

⚠️ Partial support

Only if using explicit mapping: e.g. virtual_modifiers M = 0x100; if M has the modifier index 8.

✅ Full support

Virtual modifiers that are not mapped either explicitly (using e.g. virtual_modifiers M = …) or implicitly (using modifier_map and virtualModifier) automatically use to their canonical mapping.

Multiple groups per key

✅ Full support

Contiguous identical groups are merged together.

⚠️ Not supported in the @ref RMLVO-intro "RMLVO" API

Since version 1.8 the RMLVO API does not support parsing multiple groups per key anymore, because it may break the expectation of most desktop environments and tools that the number of groups should be equal to the number of configured layouts.

See How do I define multiple groups per key? for migration instructions.

Multiple keysyms per level

❌️ Parsing only

Ignored: fallback to NoSymbol.

✅ Full support

Todo
  rationale

Multiple actions per level

❌️ No support

Parse error.

⚠️ Parsing & handling, no serialization

Currently limited to 1 action for each action type “group” and “modifier”.

Since
  1.8: Enable multiple actions per level (parsing, serializing & handling).
  1.11: Serialize to VoidAction() for compatibility with X11.

⚠️ Partial support

Currently limited to 1 action for each action type “group” and “modifier”.

Since
  1.11

Geometry

✅ Full support

⚠️ Parsing only

Rational:

- There were very few geometry definitions available in xkeyboard-config, and while xkbcommon was responsible for parsing this insanely complex format, it never actually did anything with it.
- Hopefully someone will develop a companion library which supports keyboard geometries in a more useful format, e.g. SVG.

Radio groups | ✅ Full support | ❌️ No support Unused in xkeyboard-config layouts.
Overlays | ✅ Full support | ❌️ No support Unused in xkeyboard-config layouts.
Key behaviors | ✅ Full support | ❌️ No support Used to implement radio groups and overlays, and to deal with things like keys that physically lock; Unused in xkeyboard-config layouts.
Indicator behaviors | ✅ Full support | ⚠️ Partial support E.g. LED-controls-key behavior (X11’s IM_LEDDrivesKB flag enabled) is not supported. The only supported LED behavior is key-controls-LED. Unused in xkeyboard-config layouts.

## Key actions

Key actions compatibility table
Type | Action | X11 | xkbcommon (v1 format) | xkbcommon (v2 format)
--- | --- | --- | --- | ---
Ineffectual | NoAction() | ✅ Full support | ✅ Full support
VoidAction() | ❌️ No support | ⚠️ Parsing only (since 1.10) | ✅ Full support (since 1.11)

Modifiers

SetModifiers()

⚠️ Partial support

- unlockOnPress parameter is not supported.

⚠️ Partial support

- unlockOnPress parameter is not supported. Use XKB_KEYMAP_FORMAT_TEXT_V2.

✅ Full support

- unlockOnPress parameter (since 1.11). See its documentation for further details.

LatchModifiers()

⚠️ Partial support

- latchOnPress parameter is not supported.
- unLockOnPress parameter is not supported.

⚠️ Partial support

- latchOnPress parameter is not supported. Use XKB_KEYMAP_FORMAT_TEXT_V2.
- unLockOnPress parameter is not supported. Use XKB_KEYMAP_FORMAT_TEXT_V2.

✅ Full support

- latchOnPress parameter (since 1.11). See its documentation for further details.
- unLockOnPress parameter (since 1.11). See its documentation for further details.

LockModifiers()

⚠️ Partial support

- unlockOnPress parameter is not supported.

⚠️ Partial support

- unlockOnPress parameter is not supported. Use XKB_KEYMAP_FORMAT_TEXT_V2.

✅ Full support

- unlockOnPress parameter (since 1.11). See its documentation for further details.

Groups | SetGroup() | ✅ Full support | ✅ Full support
LatchGroup() | ✅ Full support | ✅ Full support

LockGroup()

⚠️ Partial support

- lockOnRelease parameter is not supported. Use XKB_KEYMAP_FORMAT_TEXT_V2.

⚠️ Partial support

- lockOnRelease parameter is not supported. Use XKB_KEYMAP_FORMAT_TEXT_V2.

✅ Full support

- lockOnRelease (since 1.11). See its documentation for further details.

Legacy action | MovePointer() | ✅ Full support | ⚠️ Parsing and serializing only, no API support
PointerButton() | ✅ Full support | ⚠️ Parsing and serializing only, no API support
LockPointerButton() | ✅ Full support | ⚠️ Parsing and serializing only, no API support
SetPointerDefault() | ✅ Full support | ⚠️ Parsing and serializing only, no API support
SetControls() | ✅ Full support | ⚠️ Parsing and serializing only, no API support
LockControls() | ✅ Full support | ⚠️ Parsing and serializing only, no API support
TerminateServer() | ✅ Full support | ⚠️ Parsing and serializing only, no API support
SwitchScreen() | ✅ Full support | ⚠️ Parsing and serializing only, no API support
Private() | ✅ Full support | ⚠️ Parsing and serializing only, no API support
Unsupported legacy action | RedirectKey() | ✅ Full support | ❌️ Parsing only
ISOLock() | ✅ Full support | ❌️ Parsing only
DeviceButton() | ✅ Full support | ❌️ Parsing only
LockDeviceButton() | ✅ Full support | ❌️ Parsing only
DeviceValuator() | ✅ Full support | ❌️ Parsing only
MessageAction() | ✅ Full support | ❌️ Parsing only

## Keymap text format

Keymap text format compatibility table
Feature | X11 (xkbcomp) | xkbcommon (v1 format) | xkbcommon (v2 format)
--- | --- | --- | ---
Optional keymap components | ❌️ All components are mandatory | ✅ Full support (since 1.9) Keymap components are no longer mandatory, e.g. a keymap without a xkb_types section is legal.
Strong type check | ❌️ Weak type check | ⚠️ Stronger type check (WIP) Floating-point numbers cannot be used where an integer is expected.
replace merge mode in include statements | ❌️ No support | ✅ Full support (since 1.9) Supported using the prefix ^, in addition to the standard merge | and override + modes.
Keysym as strings | ❌️ No support | ✅ Full support (since 1.9) Keysyms can be written as their corresponding string, e.g. udiaeresis can be written "ü". A string with multiple Unicode code points denotes a list of the corresponding keysyms. An empty string denotes the keysym NoSymbol.
Unicode escape sequence | ❌️ No support | ✅ Full support (since 1.9) \u{NNNN}. See string literal for further information.
Extended GroupN constants | ❌️ No support Only Group1..Group8 are supported, although the resulting group must be in the range 1..4. | ❌️ No support Only Group1..Group4 are supported. Use XKB_KEYMAP_FORMAT_TEXT_V2 in order to support further groups. | ✅ Full support (since 1.11) The pattern Group<INDEX> can be used for any valid group index <INDEX>.
Extended LevelN constants | ❌️ No support Only Level1..Level8 are supported. | ✅ Full support (since 1.11) Since 1.11, the pattern Level<INDEX> can be used for any valid level index <INDEX>. Before 1.11, only Level1..Level8 were supported.
Extended include | ❌️ No support | ✅ Full support (since 1.11) Enable absolute paths and %-expansion. See keymap-include-percent-expansion for further details.
Include predefined maps | ✅ Full support | ❌️ No support The modern approach is to use RMLVO.

Exponent syntax for floating-point numbers

✅ Full support

❌️ No support

Todo
  syntax description

alternate merge mode | ✅ Full support | ⚠️ Parsing, fallback to default merge mode alternate was used in xkb_keycodes type sections and meant that if a new keycode name conflicts with an old one, consider it as a keycode alias.
Multiple group definition in symbols section | ✅ Full support | ⚠️ Supported, except in the @ref RMLVO-intro "RMLVO" API Since 1.8, only 1 group per symbol section is supported in the RMLVO API, to avoid unintuitive results. Multiple groups per symbol section is supported when parsing a KcCGST keymap.

## API

API compatibility table
Feature | X11 | xkbcommon (v1 format) | xkbcommon (v2 format)
--- | --- | --- | ---
Full Unicode support | ❌️ Incomplete | ✅ Full support Full support of simple case mappings for xkb_keysym_to_lower() and xkb_keysym_to_upper().

KcCGST

✅ Full support

⚠️ Partial support (since 1.10)

- KcCGST is considered an implementation detail, use RMLVO instead.
- Use xkb_component_names::xkb_components_names_from_rules() for debugging purposes.

XKM file format | ✅ Full support | ❌️ No support Obsolete legacy file format tied to X11 ecosystem.

# Rules support

API compatibility table
Feature | X11 | xkbcommon (v1 format) | xkbcommon (v2 format)
--- | --- | --- | ---
Partial *.pre and *.post rules files | ❌️ No support | ✅ Full support (since 1.13) See RMLVO resolution process for further details.
! include statement | ❌️ No support | ✅ Full support See rules include statement for further details.
replace merge mode | ❌️ No support | ✅ Full support (since 1.9) Support the merge mode replace via the prefix ^, in addition to the standard merge | and override + modes.

Extended layout indices

❌️ No support

✅ Full support (since 1.8)

- single: matches a single layout; layout[single] is the same as without explicit index: layout.
- first: matches the first layout/variant, no matter how many layouts are in the RMLVO configuration. Acts as both layout and layout[1].
- later: matches all but the first layout. This is an index range. Acts as layout[2] .. layout[MAX_LAYOUT], where MAX_LAYOUT is currently 4.
- any: matches layout at any position. This is an index range.
- the :all qualifier: it applies the qualified item to all layouts.

See extended layout indices for further details.

:all qualifier | ❌️ No support | ✅ Full support (since 1.8) the :all qualifier: it applies the qualified item to all layouts. See :all qualifier for further details.

Extended wild cards

❌️ No support

✅ Full support (since 1.9)

- <none> matches empty value;
- <some> matches non-empty value in every context.
- <any> matches optionally empty value in every context, contrary to the legacy * wild card which does not match empty values for layout and variant.

See rules wildcards for further information.

# Keyboard layout registry

Keyboard layout registry support
Feature | X11 | xkbcommon
--- | --- | ---

XML format

❌️ No support

✅ Full support

Todo
  rationale

# Compose support

Relative to the standard implementation in libX11 (described in the Compose(5) man-page):

Compose support
Feature | X11 (libX11) | xkbcommon
--- | --- | ---

[!] MODIFIER syntax

✅ Full support

⚠️ Parsing only

Syntax: [([!] ([~] MODIFIER)...) | None] <keysym>

If the modifier list is preceded by ! it must match exactly. MODIFIER may be one of Ctrl, Lock, Caps, Shift, Alt or Meta. Each modifier may be preceded by a ~ character to indicate that the modifier must not be present. If None is specified, no modifier may be present.

Todo
  removal rationale

Modifier keysyms in sequences | ✅ Full support | ⚠️ Parsed, but key events are ignored Modifiers should not be used in Compose sequences. Use keymap’s features or a keysym with more appropriate semantics.

Interactions with Braille keysyms

✅ Full support

❌️ No support

Todo
  feature description, removal rationale