Friday, January 04, 2008

Three 595 shift registers

A 595 shift register takes a serial byte of data and represents the eight bits in parallel digital states on eight pins. The IC can also output data in a serial fashion, allowing multiple 595's to be controlled using only three digital control pins from elsewhere.

There is an excellent tutorial by Carlyn Maw and Tom Igoe detailing how to connect two serial to parallel 595 shift registers to an Arduino board. However, this does not explicitly say how to add more. The process is very simple; all three chips share clock and latch pins from the Arduino, and the serial inputs and outputs are daisy chained together.

Although this seems (somewhat) obvious when looking at the breadboard diagrams for the two-chip example, i wanted to test this out for myself because i am wanting a total of 24 digital outputs that are controllable from the computer via the Arduino.

Here you can see the breadboard setup from a number of angles. The Arduino pin assignments are identical to the original tutorial.


The code below is a slightly modified version of the first code example from the second part of the tutorial. The modifications revolve around taking data from three incoming serial bytes and transferring these bytes to the three 595's.


//Pin connected to ST_CP of 74HC595

int latchPin = 8;

//Pin connected to SH_CP of 74HC595

int clockPin = 12;

////Pin connected to DS of 74HC595

int dataPin = 11;

byte data1;

byte data2;

byte data3;


void setup() {

Serial.begin(57600);

pinMode(latchPin, OUTPUT);


}


void loop() {

if(Serial.available() > 2) {

data1 = Serial.read();

data2 = Serial.read();

data3 = Serial.read();

digitalWrite(latchPin, 0);

shiftOut(dataPin, clockPin, data1);

shiftOut(dataPin, clockPin, data2);

shiftOut(dataPin, clockPin, data3);

digitalWrite(latchPin, 1);

}

}


void shiftOut(int myDataPin, int myClockPin, byte myDataOut) {

int i=0;

int pinState;

pinMode(myClockPin, OUTPUT);

pinMode(myDataPin, OUTPUT);


digitalWrite(myDataPin, 0);

digitalWrite(myClockPin, 0);


for (i=7; i>=0; i--) {

digitalWrite(myClockPin, 0);

if ( myDataOut & (1<<i) ) {

pinState= 1;

}

else {

pinState= 0;

}

digitalWrite(myDataPin, pinState);

digitalWrite(myClockPin, 1);

digitalWrite(myDataPin, 0);

}

digitalWrite(myClockPin, 0);

}



2 comments:

xaft said...

hi man, i got the 595´s and tried it right away.. its great! but what i do not understand is how to communicate with the outputs through max/msp..


if u could post an example it would be greatly greatly appriciated...


thanks!

Sebastian Tomczak said...

Hi there Xaft,
if you look here you can find a max patch example:


http://little-scale.blogspot.com/2008/01/talking-to-3-595s-via-maxmsp.html