A full Norwegian keyboard layout (æ, ø, å on the correct keys) for wvkbd — the on-screen virtual keyboard for wlroots-based Wayland compositors (Hyprland, Sway, etc).
Built as a variant of the deskintl layout (full-size on-screen keyboard),
with only the keys that are physically different on a Norwegian keyboard
changed:
| Key (physical position) | US layout | Norwegian layout |
|---|---|---|
| Right of P | [ { |
å Å |
| Right of L | ; : |
æ Æ |
| Right of that | ' " |
ø Ø |
Tested and in daily use on Arch Linux + Hyprland.
sudo pacman -S --needed wayland libxkbcommon pango cairo scdoc base-develImportant: the package is called
libxkbcommonin Arch's repositories, notxkbcommon(the latter is only the internalpkg-configmodule name used during the build, not the actual package name — an easy trap to fall into).
mkdir -p ~/Projects/norwegian-keyboard
cd ~/Projects/norwegian-keyboard
git clone https://github.com/jjsullivan5196/wvkbd.git .
git clone https://github.com/archruud/wvkbd-norsk.git /tmp/wvkbd-norsk
cp /tmp/wvkbd-norsk/*.h .make LAYOUT=norsk
sudo make LAYOUT=norsk installThis installs a binary called wvkbd-norsk into /usr/local/bin/. The
wvkbd source folder itself can be deleted afterwards if you want — it's
only used for building; the finished binary now lives on its own in the
system.
wvkbd-norskA keyboard should appear anchored to the bottom of the screen, full width.
Test æ/ø/å in a text field. Close with Ctrl+C in the terminal.
Adjust the height with -L (landscape) or -H (portrait):
wvkbd-norsk -L 320 # experiment to find the right height for your screenIn hyprland.lua, autostart the keyboard hidden, and use a signal to
show/hide it with a keybind:
hl.on("hyprland.start", function()
hl.exec_cmd("wvkbd-norsk -L 320 --hidden")
end)
hl.bind("SUPER + T", hl.dsp.exec_cmd("pkill --signal SIGRTMIN wvkbd-norsk"))
-- Optional: slide up from the bottom of the screen on toggle, instead of
-- just appearing/disappearing instantly:
hl.layer_rule({
match = { namespace = "wvkbd" },
animation = "slide",
})SIGRTMIN toggles visibility of an already-running instance — it doesn't
start a new process on every press, it shows/hides the one already running
in the background.
This recipe follows the exact same method used to build the Norwegian layout, and can be reused for any language with a handful of keys that differ from the US layout (Swedish, Danish, German, French, etc).
cd wvkbd
cp keymap.deskintl.h keymap.YOURLANG.h
cp layout.deskintl.h layout.YOURLANG.h
cp config.deskintl.h config.YOURLANG.hEvery standard Unicode letter has a fixed, documented XKB name (this isn't
something you guess — they're defined in X11's keysymdef.h and have been
stable for decades). Some examples:
| Letter | XKB name (lowercase) | XKB name (uppercase) |
|---|---|---|
| æ / Æ | ae |
AE |
| ø / Ø | oslash |
Ooblique |
| å / Å | aring |
Aring |
| ü / Ü | udiaeresis |
Udiaeresis |
| ñ / Ñ | ntilde |
Ntilde |
| ç / Ç | ccedilla |
Ccedilla |
Full list: run grep -i "^#define XK_" /usr/include/X11/keysymdef.h on
any Linux machine with the X11 headers installed.
Find the line for the key you want to change (search for the physical key
position, e.g. <AC10> for the key right of L). The format is:
key <AC10> { [ semicolon, colon ] };\
Replace it with your character (remember: an actual TAB character between
{ and [, not a space or the literal text \t — use a small Python
script to guarantee the correct byte format instead of editing by hand):
with open('keymap.YOURLANG.h', 'r', encoding='utf-8') as f:
lines = f.readlines()
TAB = '\t'
lines[LINE_NUMBER - 1] = f' key <AC10> {{{TAB}[ ae, AE ] }};\\\n'
with open('keymap.YOURLANG.h', 'w', encoding='utf-8') as f:
f.writelines(lines)Important: this text is part of one continuous C string spanning
thousands of lines. Every line MUST end with exactly one \ character
(line continuation) — not zero, not two. Use cat -A filename.h to compare
your line ending against an unmodified line in the same file before you're
satisfied.
Find the same physical key in layout.YOURLANG.h (search for the same
KEY_SEMICOLON/KEY_APOSTROPHE/etc. — the scancode name, not the keysym
name):
{";", ":", 1.0, Code, KEY_SEMICOLON},becomes:
{"æ", "Æ", 1.0, Code, KEY_SEMICOLON},make LAYOUT=YOURLANG
./wvkbd-YOURLANG # test directly, without installing firstDoes the right character show up when you press the right key? You're
done — sudo make LAYOUT=YOURLANG install.
Made a layout for another language? Feel free to open a pull request with
your keymap.YOURLANG.h / layout.YOURLANG.h / config.YOURLANG.h files
in this repo, so we can collect several languages in one place.
The layout files in this repo are derived from wvkbd's own deskintl
setup and follow the same license as the upstream project (see
LICENSE/COPYING in jjsullivan5196/wvkbd).