Configuration Overview
ZMK has many configuration settings that can be changed to change the behavior of your keyboard. They are set in either Kconfig or Devicetree files.
This page describes the Kconfig and Devicetree file formats and how to change settings in them. See the other pages in the configuration section for a list of settings you can change.
All configuration is currently set at compile time. After changing any settings, you must build new firmware and flash it for the changes to apply.
Config File Locations
ZMK will search multiple folders for the config files described below. There are three primary locations it will search:
User Config Folder
When building with a zmk-config
folder, ZMK will search the zmk-config/config
folder for the following config files, where <name>
is the name of the shield if using a shield, or the name of the board otherwise:
<name>.conf
(Kconfig)<name>.keymap
(Devicetree)
These files hold your personal settings for the keyboard. All files are optional. If present, they override any configuration set in the board or shield folders. Otherwise, the default configuration and/or keymap is used.
When using a split keyboard, you can use a single file without the _left
or _right
suffix to configure both sides. For example, corne.conf
and corne.keymap
will apply to both corne_left
and corne_right
. If a shared config file exists, any left or right files will be ignored.
Board Folder
ZMK will search for config files in:
zmk/app/boards/arm/<board>
zmk-config/boards/arm/<board>
<module>/boards/arm/<board>
zmk-config/config/boards/arm/<board>
(For backwards compatibility only, do not use.)
...where <board>
is the name of the board and <module>
is the root directory of any included module. These files describe the hardware of the board.
ZMK will search the board folder for the following config files in addition to Zephyr board-defining files:
<board>.conf
(Kconfig)<board>.keymap
(Devicetree, keyboards with onboard controllers only)
Shared config files (excluding any _left
or _right
suffix) are not currently supported in board folders.
For more documentation on creating and configuring a new board, see Zephyr's board porting guide.
Shield Folder
When building with a shield, ZMK will search for config files in:
zmk/app/boards/shields/<shield>
zmk-config/boards/shields/<shield>
<module>/boards/shields/<shield>
zmk-config/config/boards/shields/<shield>
(For backwards compatibility only, do not use.)
...where <shield>
is the name of the shield and <module>
is the root directory of any included module. These files describe the hardware of the shield that the board is plugged into.
ZMK will search the shield folder for the following config files in addition to Zephyr shield-defining files:
<shield>.conf
(Kconfig)<shield>.keymap
(Devicetree)
Shared config files (excluding any _left
or _right
suffix) are not currently supported in shield folders.
For more documentation on creating and configuring a new shield, see Zephyr's shield documentation and ZMK's new keyboard shield guide.
Kconfig Files
Kconfig is used to configure global settings such as the keyboard name and enabling certain hardware devices. These typically have a .conf
file extension and are text files containing CONFIG_XYZ=value
assignments, with one setting per line.
Kconfig files look like this:
CONFIG_ZMK_SLEEP=y
CONFIG_EC11=y
CONFIG_EC11_TRIGGER_GLOBAL_THREAD=y
Files ending with _defconfig
use the same syntax as .conf
files. They set the default configuration for the hardware, which is then overridden by anything in a .conf
file.
The list of available settings is determined by various files in ZMK whose names start with Kconfig
. Note that options are not prefixed with CONFIG_
in these files.
See Zephyr's Kconfig documentation for more details on Kconfig files.
You can investigate the final set of configuration settings that are in effect during a build to diagnose any issues with changing Kconfig settings.
KConfig Value Types
bool
Either y
for yes or n
for no.
Example: CONFIG_FOO=y
int
An integer.
Example: CONFIG_FOO=42
string
Text surrounded by double quotes.
Example: CONFIG_FOO="foo"
Devicetree Files
Various Devicetree files are combined to build a tree that describes the hardware for a keyboard. They are also used to define keymaps. A full primer on Devicetree can be found in the Devicetree Overview page -- a shorter summary of some of the points can be found below.
Devicetree Overview
Devicetree files use various file extensions. These indicate the purpose of the file, but they have no effect on how the file is processed. Common file extensions for Devicetree files include:
.dts
: The base hardware definition..overlay
: Adds to and/or overrides definitions in a.dts
file..keymap
: Holds a keymap and user-specific hardware configuration..dtsi
: A file which is only intended to be#include
d from another file.
Devicetree files look like this:
/ {
chosen {
zmk,kscan = &kscan0;
};
kscan0: kscan {
compatible = "zmk,kscan-gpio-matrix";
};
};
Devicetree properties apply to specific nodes in the tree instead of globally. The properties that can be set for each node are determined by .yaml
files in ZMK in the various dts/bindings
folders.
See Zephyr's Devicetree guide for more details on Devicetree files.
You can investigate the final combined Devicetree produced during a build to diagnose any issues with changing Devicetree nodes.
Changing Devicetree Properties
Since Devicetree properties are set for specific nodes in the tree, you will first need to find the node you want to configure. You will typically need to
search through the .dts
file for your board, .overlay
file for your shield, or a .dtsi
file included by those files using an #include
statement.
A Devicetree node looks like this:
kscan0: kscan {
compatible = "zmk,kscan-gpio-matrix";
// more properties and/or nodes...
};
The part before the colon, kscan0
, is a label. This is optional, and it provides a shortcut to allow changing the properties of the node. The part after the colon, kscan
, is the node's name. The values inside the curly braces are the node's properties.
The compatible
property indicates what type of node it is. Search this documentation for the text inside the quotes to see which properties the node
supports. You can also search ZMK for a file whose name is the value of the compatible
property with a .yaml
file extension.
To set a property, see below for examples for common property types, or see Zephyr's Devicetree documentation for more details on the syntax for properties.
To change a property for an existing node, first find the node you want to change and find its label. Next, outside of any other node, write an ampersand (&
)
followed by the node's label, an opening curly brace ({
), one or more new property values, a closing curly brace (}
), and a semicolon (;
).
For example, to adjust the debouncing of the zmk,kscan-gpio-matrix
node shown above, you could add this to your keymap:
&kscan0 {
debounce-press-ms = <0>;
};
If the node you want to edit doesn't have a label, you can also write a new tree and it will be merged with the existing tree, overriding any properties. Adding this to your keymap would be equivalent to the previous example.
/ {
kscan {
debounce-press-ms = <0>;
};
};