Rotary encoders measure the angular position of a shaft or axle. The main difference and asset is that they are absolutlely free to keep on turning in one direction forever, where as other rotation sensors are limited to a finite amount of turns before they have to go the other way. That is a real bonus for long term sensing, or high speed sensing. Using programming (either on the board or on a receiving machine) techniques it is possible to measure the direction and speed of rotation. Good encoders are extremely rugged and highly accurate and can be used effectively for a wide range of physical computing tasks. The encoder I have used on projects is the interestingly named AMT 103-V which you can get from digikey. I originally found out about them from this .pdf about high speed encoders from phidgets. A good paragraph below taken from the .pdf explains how the encoder works.
'The most common type of incremental encoder uses two output channels (A and B) to sense position. Using two sensors on a standard optical grating positioned 90 degrees out of phase, the two output channels of the quadrature encoder indicate both incremental position and direction of rotation. If A leads B, for example, the disk is rotating in a clockwise direction. If B leads A, then the disk is rotating in a counter-clockwise direction. By monitoring both the number of pulses and the relative phase of signals A and B, you can track both the position and direction of rotation.'
So it is relatively simple to make a program to read an encoder. I have written a small program for arduino that is adapted only slightly from the excellent tutorial available here on the Arduino site.
Code below uses an AMT 103-V attached to pin 2 (A) and 4 (B), it works out the angular position from 0 to 256. It is read out as serial and can be read in to processing etc... The figure that comes back is 0 to 4096 which is the resolution of one full turn. This is divisible by 16 to make 256 which can then be worked into a 360 degree figure if you need. I guess those calculations might best be handled by the receiving machine to keep up the speed.
// find angular position of encoder int encoder0PinA = 2; int encoder0PinB = 4; int val; volatile int encoder0Pos = 0; void setup() { Serial.begin(9600); pinMode(encoder0PinA, INPUT); digitalWrite(encoder0PinA, HIGH); pinMode(encoder0PinB, INPUT); digitalWrite(encoder0PinB, HIGH); attachInterrupt(0, doEncoder, CHANGE); // using interrupt to call doEncoder function } void loop(){ val = encoder0Pos; //Serial.println(val); serialWrite('A'); // Identifier for serial reading printInteger(val); serialWrite(10); delay(200); // below brings counter number back down to 0 after a 360 turn number below // will depend on resolution of encoder. if (encoder0Pos > 4096){// figure depends on encoder encoder0Pos = 0; } if (encoder0Pos < 0){ encoder0Pos = 4096; } } void doEncoder(){ if (digitalRead(encoder0PinA) == HIGH) { if (digitalRead(encoder0PinB) == LOW) { encoder0Pos = encoder0Pos - 1; } else { encoder0Pos = encoder0Pos + 1; } } else { if (digitalRead(encoder0PinB) == LOW) { encoder0Pos = encoder0Pos + 1; } else { encoder0Pos = encoder0Pos - 1; } } }