banner

The Nintendo Wii Remote (aka wiimote) is one of my preferred gamepad to play old console emulators.

Why? Well, it uses bluetooth, probably you already have one (if you had a Wii), and if you hold it in the landscape position, it mimics a 8-bit gamepad. And additionally to the side buttons 1 and 2, it offers buttons like A, B, Home, + and -. Perfect to play NES, Sega Master System, Sega Genesis, NeoGeo and others that do not require more buttons than that.

XWiimote

In the past, Linux (mainly Ubuntu) offered several ways to support wiimote, all using custom event handling: CWiiD, Wiiuse, WiiCan and others.

Some of them are a bit abandoned, and do not rely on Linux event handling.

It’s where XWiimote comes to the rescue. According the official page:

XWiimote is an open-source linux device driver for Nintendo Wii / Wii U Remotes … that tries to supercede cwiid, wiiuse and others by integrating the driver into existing linux infrastructure.

xf86-input-xwiimote

The XWiimote is a raw driver: it only reads the data sent by the wiimote. I.e., it lackes additional configurations

Fortunately, the same authors created xf86-input-xwiimote, which is a X.Org driver built over the xwmiimote, which provides several configurations options.

Install

We can find both programs available in default Ubuntu 16.04 (Xenial) install.

Unfortunatelly, on 14.04 (Trusty) package xwiimote is an old version and xf86-input-xwiimote is not available (because it relies on xwiimote version 2). I tried to compile xwiimote (version 2) and xf86-input-xwiimote, but the later didn’t work (always crashing).

So, if you’re using 16.04 (Xenial) install both with:

sudo apt-get install xwiimote xserver-xorg-input-xwiimote

If you’re using Ubuntu 16.04.1 or above and your system is reporting broken dependencies, check this post to properly install.

Configuration

Now we’ll configure the wiimote to fire some keyboard keys while buttons are pressed. This will make it work in every program that supports keyboard as control.

Using sudo (or root) edit /usr/share/X11/xorg.conf.d/60-xorg-xwiimote.conf file, adding all below lines in the Identifier "Nintendo Wii Remote" section:

        Option "MapLeft" "KEY_DOWN"
        Option "MapRight" "KEY_UP"
        Option "MapUp" "KEY_LEFT"
        Option "MapDown" "KEY_RIGHT"
        Option "MapA" "KEY_A"
        Option "MapB" "KEY_B"
        Option "MapPlus" "KEY_EQUAL"
        Option "MapMinus" "KEY_MINUS"
        Option "MapHome" "KEY_ESC"

Save it.

Your 60-xorg-xwiimote.conf file should be now similar to this:

# X11 xorg xf86-input-xwiimote config
# Load correct xwiimote driver for all connected Nintendo Wii Remotes.
# Overwrite previous blacklist.
# We do not load the driver on unsupported extensions. This currently includes
# independent extension like classic-controller and pro-controller. Instead, the
# evdev driver is loaded (there is no way to negate InputClass Match* rules..)

Section "InputClass"
        Identifier "Nintendo Wii Remote"
        MatchProduct "Nintendo Wii Remote"
        MatchDevicePath "/dev/input/event*"
        Option "Ignore" "off"
        Driver "xwiimote"
        Option "MapLeft" "KEY_DOWN"
        Option "MapRight" "KEY_UP"
        Option "MapUp" "KEY_LEFT"
        Option "MapDown" "KEY_RIGHT"
        Option "MapA" "KEY_A"
        Option "MapB" "KEY_B"
        Option "MapPlus" "KEY_EQUAL"
        Option "MapMinus" "KEY_MINUS"
        Option "MapHome" "KEY_ESC"
EndSection

Section "InputClass"
        Identifier "Nintendo Wii Remote Classic Controller Whitelist"
        MatchProduct "Nintendo Wii Remote Classic Controller"
        MatchDevicePath "/dev/input/event*"
        Option "Ignore" "off"
        Driver "evdev"
EndSection

Section "InputClass"
        Identifier "Nintendo Wii Remote Pro Controller Whitelist"
        MatchProduct "Nintendo Wii Remote Pro Controller"
        MatchDevicePath "/dev/input/event*"
        Option "Ignore" "off"
        Driver "evdev"
EndSection

Restart X.org

You’ll need to restart your X.org to get all changes working. Usually in Ubuntu, a logout/login is enough.