Wednesday, March 27, 2013

rbdrum2midi

Its fun to hit stuff. Which is why drumming is so therapeutic. However dums may seems cost prohibitive to many of us. I too have felt that. However there is hope! For a few bucks at a local garage sale you can probably find folks getting rid of their old drum rockband drum sets for various gaming systems. This gives you something to hit, but it doesn't sound much like a drum. But could it?

Would I really be setting you up like this if it couldn't?


So my brother upgraded his drumkit and gave me the old one. I had been scoping them out at the thrift stores and garage sales in town, but for me even $10 is cost prohibitive most of the time. So this was  a big boon! I got it home and plugged it in and started JACK and... Nothing. Of course it didn't work. You may as well plug in your usb mouse and hope for a midi connection to pop up. You need a driver for the drumkit.

I'm not the first one to want to do this. By making the drum output JACK or ALSA midi signals it could be connected to Hydrogen, any sample drumkit pack in LinuxSampler, a drum machine plugin or a stage light controller (not sure why you would but you could).

After a mentionable survey of what drivers existed I found one here that seemed promising. I found someone else who had taken it and remapped the midi output and added support for cymbals.

I downloaded the project and couldn't get it to build. After several tries at getting configure and make to play along I resorted to simply running gcc in the terminal since there's only one file to compile and it only needed 2 linker flags. For some reason its particular about the linker flag order or something. I ran it (must be super) and still no midi output! Sadness reigned.

Luckily the code did have a verbose mode which I ran and saw that my rockband 1 drumkit gives entirely different data output than the rockband 2 or 3 drumkits the previous developers used. So, when you have the source and it doesn't work for you what do you do?...

Patch it! I actually went so far as to totally revamp the code because I could see some things that might optimize the latency and at worst just make it more readable. For optimizations, it was really just breaking up several of the if statements, i.e. the drumset type isn't going to change between callbacks, so why check each time? check before you assign the interrupt routine and just assign a different callback function dependant upon set type. Most of the changes are probably not measureable, or at least I didn't measure the before and after, so I'm not going to make any real performance improvent claims.

More importantly I think, is that I tried really hard to make good use of #defines to make the code much more readable. So I think. Readable is somewhat subjective, though I think most would agree that
bass = RB_ORANGE;
is easier to understand the logic of than
bass = buf[0] & 0x10;
.

Anyhow I also added support for rockband 1 drumsets. They don't have velocity information so each hit has a velocity of 120. If you want velocity, you gotta get a rockband 2 or 3 set. Not a free rockband 1 set from your brother. Oh well, can't beat free. You could also use a guitar hero world tour drum set, which interestingly has support for velocity in the bass pedal as well, at the cost of only 3 drumheads. It also has unique cymbal colors though (whereas rockband cymbals are the same color as three of the four drumheads). The implications of this for rockband drumset users is that you cannot actually hit the green drumhead at the same time as the cymbal. It may intelligently send two messages in quick succession if you try this, but I doubt it.

Also added was support for assigning whatever midi signals you want to each drumhead. Without recompiling even. The guide for the command options is shown if you just run the program with the -h option. The default assignment is what I use for playing the Yamaha vintage kit in Hydrogen, which is fine, but lately I've been enjoying the Salamander drumkit in my music, which is an entirely different mapping. So with my changes I just made a separate little one click script to map the drumkit to the salamader:

#!/bin/bash
gksudo ./rbdrum2midi -rb1 -r 40 -y 42 -b 55 -g 43


Of course, you could have figured all that out easily enough from looking at the source, I'm sure. With all my new variable names and everything. I'm so awesome.... right?... Eh, I'm ok at least. Hopefully I didn't break anything so PLEASE test it if you can especially if you have a wii or xbox rockband 2 or 3 drumset, and let me know how it goes. If it doesn't work, start it in verbose mode and send me the output for each drum hit, and I can fix it up for you, because radomas added me as a maintainer! So check it out. FLOSS forever! It makes your teeth last longer.

No comments: