Links

pmuellr is Patrick Mueller

other pmuellr thangs: home page, twitter, flickr, github

Saturday, October 18, 2008

webimidi

As a reader of the great blog create digital music, I've been reading about and playing a bit with all the great Nintendo DS music software, and just reading about the iPhone/touch software (I am currently iPhone/iTouch challenged). Fun stuff.

Of most interest to me are MIDI controllers; hardware or software that you can use to control some other software via the enduring MIDI protocol. Having a MIDI controller on a portable device is a great idea; the more devices you have available, the better. But one of the problems with MIDI controllers is that there's never one that fits your needs exactly. Most of the existing handheld software is fairly fixed function.

So what I really want is some software that easily lets me construct a MIDI controller that does exactly what I want. That I can use on one of my portable devices: a Nokia N800 and a Nintendo DS.

There are two general problems to solve: making it easy to construct a new controller, and getting input from handheld into a MIDI device on my desktop where my music software is running.

At some point it struck me that having the MIDI controllers implemented as UIs that can run in a web browser solves some of the general constraints. Writing UIs in HTML, CSS, and JavaScript is (to some extent) easier than writing to native GUI toolkits. Plus, there's the hope of writing a UI once and being able to reuse it on several devices. Writing code specific to an iPhone doesn't help me if I later want to run it on a Nokia N800 or Nintendo DS later.

On the MIDI side, providing an HTTP interface on the desktop to MIDI devices make it easy to interface to them from other devices. There are some existing ways to interface with MIDI over tcp/ip, including Network MIDI (RFC 4695 and RFC 4696; Apple provides an implementation of these protocols, but doesn't document some of the control messaging bits) and DSMI. But none of these actually flow over HTTP, and it just seems so appropriate to actually surface the interface over HTTP. Duh.

And thus, webimidi is born.

Below is a movie of the single device that I've included with the code, which is a simple two octave keyboard.

I wrote webimidi in Python, although I was tempted to use the Ruby MIDI interface that Giles Bowkett's provides in Archaeopteryx, but that would have been too easy. ha ha. Actually, I've been feeling more python-y lately than ruby-y, and this was a great excuse to learn two parts of Python I haven't played with:

  • ctypes - a foreign function interface (FFI). ctypes allows you to interface with native shared libraries, the native data structures they use, etc. The world (of C) is your oyster.

  • wsgi - Python's Web Server Gateway Interface. For folks familiar with Java, wsgi is the "servlet" of the Python world.

Currently, webimidi only runs on Mac OS X, and probably only 10.5. Porting to Windows would really just be a matter of doing a ctypes interface to Windows MIDI functions (I did this MANY years ago in Smalltalk; it's doable, I just have no interest in actually doing it today).

Up next, a controller for my Line6 TonePort UX1. Also, seeing if I can get something useful to run on my Nintendo DS; not clear that it supports XmlHTTTPRequest, which is currently a pre-req for controllers built like this.