A forward-compatible gamepad using 3d printed cases. This controller is inspired by the many smartphone gamepads and and game-focused phones that have come and gone. New phones come out, more powerful hardware arrives, and the old products are left underspecced or incompatible.
The current version uses an nrf51822 SoC for CPU and bluetooth.
Work in progress. There are several planned versions (if it makes it that far). v1 is for my personal use. v2 is community involvement and support for multiple phones. v3 extends functionality beyond just a gamepad.
I want to play action/platformer games on my phone. The straw that broke the camel's back was "Prinny: Can I Really Be the Hero?" - I couldn't beat a boss because my fingers kept missing the intangible touchscreen controls. I want a gamepad that is compact to carry, comfortable to hold, and works with multiple phones.
Current plan is an nrf51822 based gamepad in a 3d printed case. Users will be able to 3d print a case for their particular phone and drop in the electronics. When the user gets a new phone, a new case can be made and the electronics transferred.
Here's the current state of development. The test hardware mostly works! I've been using through-hole components on perfboard and connecting them to the WT51822-S2 with magnet wire. My soldering skills are low but it's getting the job done. Inspiration comes from NE555's beautiful perfboard work.
Here's an early pic with no wiring.
Current version's backside. The ground wire runs around the perimeter so that I can easily wire buttons to ground. Two buttons don't work - I probably didn't strip the enamel well enough for those wires - but all the rest works.
Close up to the module:
Ugly soldering but functional. The low temp enameled wire is pretty easy to work with (I had some high temp and gave that up very quickly). Flux and tin the contact. Strip and tin the end of the wire with a blob of solder. Solder the wire to the contact. Helping hands would make this easier to solder.
I modeled this grip in Fusion 360 and 3d printed on our CEL Robox.
Those pegs were meant to hold the perfboard. They broke off in a heartbeat. In their place I tapped some nails through the grip to hold the board. The grip itself isn't really comfortable but it's better than holding the perfboard. Good enough - I'll conserve my effort for other tasks.
Here you can see the BlackMagic Probe reflashed STM32 that I'm using for development. SWD is used for programming and UART for serial output, both running simultaneously on the same device thanks to BMP firmware.
The software sorta works. I'm using Gamepad Tester on Android to verify.
Using mbed OS I managed to get it to work although there are some bugs and quirks. Fixing these are my main work right now
RAM usage - Mbed + the SoftDevice (Nordic's BLE stack) runs dangerously close to 16k RAM. Newer versions of mbed will throw out-of-memory errors. Build 131 has been working fine. Unfortunately mbed dropped support for SoftDevice S110 which uses 2k less RAM. According to some guide (which I lost, gotta re-find that) I should be able to allocate less RAM to the SoftDevice in the linker as long as I don't use the Central role.
HID Report Descriptor - My HID Report Descriptor isn't working with multiple bytes. The BLE API gives me BLE_ERROR_INVALID_STATE when I try, even when using the working source from Ozan's nrf51822 controller. I have a vague idea what the issue is. Right now I'm using a single byte, with 1 bit per button. This is my main priority since I need to send the d-pad buttons separately from the regular buttons - either as a pair of X/Y axis or as a hat switch.
Windows 10 quirks - Win10 has two issues. First is that the buttons aren't coming through to the gamepad configuration thing. Second is that sometimes the BLE will instantly disconnect after connecting. For now I'm simply ditching Windows as a target. It would be nice for testing but in the end this all intended for Android use. I have no idea what's causing either issue.
That's all for now! More updates later when I have some solid software written.
My core51822's headers have been annoying me for a while. I did get a cable to convert these 2mm pitch headers. Unfortunately (or maybe fortunately) I accidentally killed the board! Whoops. I'll keep this log short since the cable isn't relevant to the project anymore - full details are on my blog.
It's a 44-pin laptop IDE cable. The original connector is 2x24. I sawed it half, mangling only a few of the rows and leaving me with a 2x10 and 2x11 connector. Just right for the core51822's 2x9 headers. The wire is stranded which doesn't play nicely with the breadboard - before using it I soldered a tiny bit of solid wire to the end. I should've bought the longer cable - mine is 2", I should've bought the 8".
Anyway I killed that board so it's on to the next board:
This one is a little harder to find info on but I believe it's a Wireless-Tag WT51822-S2 module. At the very least Wireless-Tag has the best documentation on the chip. I'll put this module on perfboard and try to get an actual functioning controller.
After way too much struggling I'm abandoning nrf5 SDK in favor of mbed OS. The Nordic tutorials are sorely lacking. The example code doesn't help since I don't have in-depth knowledge of BLE packet structure. Even if I persist and get it working, the barrier to entry will make it more difficult as a community project: harder to maintain, contribute to, or fork. Meanwhile mbed OS supports the nrf51822 and is MUCH easier.
-sign up for https://os.mbed.com/compiler -new project -when it asks for a board, follow the link, find "nrf51822" which is 16k (use the BLE checkbox in the filters on the left) -click, add -create a new test project. My template was BLE_Button, you can use whatever you want -hit Compile. It'll compile (rather quickly!) and provide a flashable .hex file -download the file, load and run it with gdb it works!
Importing the BLE HID library -click Import -Libraries tab -search "BLE" -find "BLE_HID", double click to import into project
So far I've only used mbed's online IDE and compiler. It's not mind blowing but it's better than Notepad. There is a project gcc4mbed which I can try later with Eclipse, but right now my focus is on getting a prototype.
There are a few versions of mbed OS availble right now. The 16k nrf51822 chips require mbed OS 2 (mbed classic) due to limited RAM. I don't think it will impact the project at all, it seems like the latest OS features are intended for networked/IoT applications. mbed classic has plenty of features and has already simplified my job.
Ozan's arcade controller code is already working but I'm going to try rewriting it from scratch so that
a) I learn C++,mbed, and the HID library
b) I can license the code myself (instead of being a derivative of ARM Ltd's Apache-licensed code)
The code is so straight-forward that I can't reasonably re-write it. I'll just make it a derivative work.
Here's how to get applications for the nrf compiling on Windows. Linux and Mac users will require some small changes the home directory (%USERPROFILE% to ~), serial port (COM8 to /dev/ttyACM0), etc. I'm still working on some of these settings - I'll add it to a Github Wiki later for updating and versioning.
I assume that all makefiles are written for gcc 4.9.3 so I specifically got that version (4_9-2015q3). I only needed to change my GNU_INSTALL_ROOT variable. I might change this later to match Eclipse, once that is finally configured.
PROGFILES lines were not needed. I didn't need to make any changes to Makefile.common
Configure makefile to match chip
I went to compile the example programs and found more directories such as "pca10028" etc. There are different types of nRF5* chips and these extra directories are the particular dev boards. The latest SDK should work for this chip, it's just not configured by default. So we make some tweaks.
Finding chip model
My two modules have chips:
to find your chip details, check the chip marking (source):
Packet variant and the first two digits in the build code can be read from markings on top of the nRF51 IC.
aka only "h0" and "h1" are actually written on the IC. The last digit is not written.
so now with the chart I know all my chip details
packet variant: qfaa
build code: h00 and h10
These specs match the pca10001 development board. The latest SDKs don't have samples for the pca10001 but they do have samples for the similar pca10028 (nrf51422). I still don't know exactly which SDK or SoftDevice is ideal for this project.
I'll be using Black Magic Probe to program/debug my "core51822" nrf51822 modules. Cheap STM32 boards can be flashed with the BMP firmware. (Note: Maple Mini board didn'twork, stick to STM32F103C8T6 boards). HaD gave a brief summary about BMPs:
-STM32F103C8T6 ($3) + FTDI serial adapter clone ($2) + core51822 or similar modules ($6) = $11
-NRF51 DK ($34)
-Segger J-Link EDU ($60 not incl shipping) + core51822 or similar modules ($6) = $66+
The STM32 parts were sourced from China. It'll be $15-$20 if shipped from the US. I already had the serial adapter from the Arduino work so this was cheapest route bay far. Also I swear the NRF51 DK was $100 when I first checked and that's why I went the STM32/core51822 route. Now it's only $34. This is a very tempting option since it's officially supported and easier to set up. The DK has SWD pins so it can flash other modules as well.
On to the Black Magic Probe flashing. All of the guides were for Linux so I used my VM, Thinking about it now I probably could have compiled using the Windows build of gcc. Oops, too late. If other people get into this I'll find/write a build script so that people can download the prebuilt firmware.
Have the STM32 plugged in, start Zadig, select Black Magic (Upgrade) in the dropdown, use the arrows to select libusbK, install driver. VirtualBox still didn't pass through, and I'm being dumb and lazy, so I just used the dfu-util Windows build and transferred blackmagic.bin to Windows. Use dfu-util v0.9. Some other guide I had been following used v0.6 but that caused issue for me.
Phone case design time. I'll be 3d printing this, first in ABS, then in TPU, and eventually using it as a daily driver. I chose Fusion 360 this time to make it easier to edit the model. This is sooo much better than Sketchup, doesn't royally screw the model when I apply fillets, and it allows me to suppress feature later in development.
The "test" version with top lip removed so that I can print in hard ABS and a filament-saving space:
This will be printed on a CEL Robox using ABS. If the test print goes well then I'll print in TPU. I group bought a printer with friends but it's currently down. I'm waiting for my friend to calibrate the bed after installing a new sticky print bed. We'll still have to mod the feed system to work with TPU.
I documented my prior attempt but the results weren't great. Here's the summary for historic purposes. This is my first real electronics project so I wanted it easy. I used an Arduino with an HC-05 Bluetooth module reflashed with RN-42 firmware, and Sketchup for the phone case modeling. The HC-05 worked but I don't think that reflashing the firmware is appropriate for a community project. Sketchup was entirely inadequate.
I ordered parts, breadboard components, and soldering iron. I learned microcontroller basics on the Arduino - blinking LEDs, voltage dividers, button input, debouncing buttons, pull up / pull down, bitpacking. The Arduino was great for learning that. I re-learned soldering which I haven't done in years, and breadboarding. Pro tip, don't buy bottom of the barrel jumpers, half of mine are dead and it caused endless frustration.
I got the controller to show as an HID gamepad in Windows. This is where I stopped with the Arduino/HC-05 and ordered nrf51822 gear. It can definitely work, I just don't think it's ideal.
Here's the phone case I started for my Nexus 6P. My friends and I had already been using Sketchup for other projects however it turned out to be a poor choice for small models - I had issues with keeping faces flat and with Sketchup combining nearby lines.
My new attempt is using the nrf51822 BLE SoC and Fusion 360. I got nrf51822 compiling and flashing working but no code of my own yet. I've made great progress with Fusion 360, parametric modeling rocks. More updates to come.