You can import keyboard layout definitions from different sources:
- A large collection of keyboard layouts can be found in the CLDR project, and we have tools to parse those.
- You can also import keyboard layouts produced by the Kalamine project.
- If none of these are available, you can write your own layout definition files.
Whatever path you choose, the entry point to adding new keyboard layouts is the keyboard-layout-generator package.
It contains the scripts which take keyboard layout definitions in various formats and generate TypeScript files with the same layouts converted into our own internal representation.
To start the generator, run the following shell commands:
cd packages/keybr-keyboard-generator
npm run generateThe generator will write files to packages/keybr-keyboard/lib/data/layout. You should not modify the generated files, as your changes will be lost if the generator is run again.
Custom keyboard layout definition files are located in packages/keybr-keyboard-generator/lib/layout.
You can add your own keyboard layout by copying and modifying an existing one. The configuration format is straightforward, each physical key location (like "KeyA", "KeyB", etc.) is mapped to a list of up to four code points.
The four code points are given for the following key modifiers:
- No modifier.
Shiftmodifier.AltGrmodifier.Shift+AltGrmodifier.
The code points can be given as:
- A string of up to four characters long.
- An array of up to four strings or numeric code point values.
export default {
KeyQ: "qQ",
KeyW: ["w", "W"],
KeyE: [0x0065, 0x0045],
// ... more keys ...
};Your keyboard layout can also include dead keys.
A dead key can be configured as a combining diacritical mark code point:
export default {
KeyQ: [
/* COMBINING GRAVE ACCENT */ 0x0300,
/* COMBINING CIRCUMFLEX ACCENT */ 0x005e,
],
// ... more keys ...
};Or as a printable diacritical mark string prefixed with the "*" character:
export default {
KeyQ: ["*`", "*^"],
// ... more keys ...
};Please note that for simplicity we only support dead keys which combine base characters with diacritical marks. We do not support dead keys which switch between different alphabets, produce non-letter characters, etc.
The generated layout files contain only mappings to code points. Each layout must also have an id and a name, and these are configured elsewhere.
To complete a layout configuration, add a new entry to the Layout class defined in packages/keybr-layout/lib/layout.ts.
static readonly EN_CUSTOM = new Layout(
/* id= */ "en-custom",
/* xid= */ 0xff,
/* name= */ "My Custom Layout",
/* family= */ "qwerty",
/* language= */ Language.EN,
/* emulate= */ false,
/* geometries= */ new Enum(
Geometry.STANDARD_102,
Geometry.STANDARD_102_FULL,
Geometry.STANDARD_101,
Geometry.STANDARD_101_FULL,
Geometry.MATRIX,
),
);Give the layout a name, select a unique id and xid
(Just increase the largest xid of an existing layout by one.)
id is a human-readable string that we store in JSON files.
xid is a single-byte numeric identifier that we store in binary files.
Once assigned, these identifiers must never change.
Lesson results from different keyboard layouts that belong to the same layout family are combined and show together.
Otherwise, switching from the United States to the United Kingdom would invalidate your previous results as if you switched to a completely new layout.
However, since these two layouts belong to the same family "qwerty", this is not the case.
The most common families are "qwerty", "qwertz" and "azerty".
If your layout does not belong to any of these families, you must select a custom family.
The language option allows filtering all available layouts by a selected language.
The emulation option can be enabled if your layout does not include dead keys.
The geometries option allows the selection of the enabled layout geometries, such as ISO, ANSI, etc. Some layouts are only available with a specific geometry, such as matrix.
The first listed geometry is the preferred one.