Using Arduino and Pd for musical live performance
Connecting an Arduino microcontroller to Pd is no big problem: You can just put Firmata on your Arduino and use the Pduino library for communication on the Pd side.
But sometimes Firmata is not the answer to every problem: You may want to turn on the built-in pull-up resistors for digital input pins, you may want to do some calculation on the Arduino before sending a message, or you may want to send a message from Arduino to Pd only on change.
In fact, I wanted to do all of the above, but not use Arduino for output. This led to the following electronics and code.
Connecting Inputs to Arduino
I have connected several push buttons to the Arduino, and one variable resistor. All push buttons are open an close on push. All connected devices:
- Three foot switches in a box.
- Three push buttons and a force-sensitive resistor mounted on a glove, worn on the right hand.
- A keypad consisting of 12 push buttons with a resistor matrix similar to this setup (in German). The main difference in my setup is the usage of values ten times as in the example, as the thin cables have a non-negligable resistance. This is mounted on my left forearm
Schematics

The Arduino Shield



The Glove



The Stompbox


The Keypad


Later Modifications Using Flex Sensors


Message Passing between Arduino And Pd
I wanted to minimize the data sent from Arduino over USB to the host computer. I came up with the following "protocol", that uses 1 byte for a digital value and 2 bytes for analog values.
- Digital message
100ppppv
- Analog message
11pppvvv 0vvvvvvv
p
denotes bits used for encoding the pin number, v
bits used for values.
As the Arduino Duemilanove - the one that I use - has 14 digital pins, 4 bits (0-15) are necessary to encode the values, 6 analog ins can be encoded in 3 bits (0-7). Digital pins only read 0 or 1, so only one bit is needed for encoding the value, analog pins read values 0-1023, which corresponds to 10 bits.
If a byte starts with a value of 11, then this byte and the following one starting with 0 together are an analog message. If a byte starts with 100, then the message is a digital message.
On Pd's side, messages are parsed and then output in the same way as [pduino]
does it: (a|d) [pin number] [value]
. That design allows you use it as a drop in replacement.
I first tried to parse messages with bit shifting and [expr]
, but that was too CPU intensitive, so I have created my own external in C. That external does the bit shifting and then outputs messages as lists.
Pd Patch
I am using the setup mostly for live performances, and the demo patch included in the source code is the actual patch that I use. It also makes heavy use of my abstractions.