how to drive 25 led with 5 pcs of 595 shift register?

Hi,
I need to control 25 led's, one after another. Everything is fine with 2x 595 and 16 leds, but I don't know how to add another 3x 595 and rest of led's :~
When I add third 595 it light up all led's connected to it after last led in second 595.

/*

 Created 23 Mar 2010
 by Tom Igoe

 */

//Pin connected to latch pin (ST_CP) of 74HC595
const int latchPin = 8;
//Pin connected to clock pin (SH_CP) of 74HC595
const int clockPin = 12;
////Pin connected to Data in (DS) of 74HC595
const int dataPin = 11;

void setup() {
  //set pins to output because they are addressed in the main loop
  pinMode(latchPin, OUTPUT);
  pinMode(dataPin, OUTPUT);  
  pinMode(clockPin, OUTPUT);

}

void loop() {
  
    int bitToSet = 0;

  // write to the shift register with the correct bit set high:
  for (bitToSet=0; bitToSet<16; bitToSet++){
    registerWrite(bitToSet, HIGH);
  delay(300);
}
  
}

// This method sends bits to the shift register:

void registerWrite(int whichPin, int whichState) {
// the bits you want to send
  unsigned int bitsToSend = 0;

  // turn off the output so the pins don't light up
  // while you're shifting bits:
  digitalWrite(latchPin, LOW);

  // turn on the next highest bit in bitsToSend:
  bitWrite(bitsToSend, whichPin, whichState);

  // break the bits into two bytes, one for 
  // the first register and one for the second:
  byte registerOne = highByte(bitsToSend);
  byte registerTwo = lowByte(bitsToSend);

  // shift the bytes out:
  shiftOut(dataPin, clockPin, MSBFIRST, registerOne);
  shiftOut(dataPin, clockPin, MSBFIRST, registerTwo);
  
    // turn on the output so the LEDs can light up:
  digitalWrite(latchPin, HIGH);

}
  1. use 2 hc595s to drive up to 64 leds;
  2. save the remaining 3 hc595s for future projects.

Double the hardware chain, call this twice? Make it just 9 vs 16.

  int bitToSet = 0;

  // write to the shift register with the correct bit set high:
  for (bitToSet=0; bitToSet<16; bitToSet++){
    registerWrite(bitToSet, HIGH);
  delay(300);
}

You have proper decoupling on all these 595's and a powerful enough power supply? There shouldn't be problems daisy-chaining them upto 10 or so (so long as all wiring is short). For 25 LEDs you only need 4 shift registers.

CrossRoads:
Double the hardware chain, call this twice? Make it just 9 vs 16.

  int bitToSet = 0;

// write to the shift register with the correct bit set high:
 for (bitToSet=0; bitToSet<16; bitToSet++){
   registerWrite(bitToSet, HIGH);
 delay(300);
}

I use another arduino pin for additional two 595 data line. clock and latch are connected to same arduino pins as first pair of 595.
add slightly changed registerWrite to sketch and IT'S ALIVE! :grin:
25 led goes like the way I wanted! Thanks for direction!

MarkT:
You have proper decoupling on all these 595's and a powerful enough power supply? There shouldn't be problems daisy-chaining them upto 10 or so (so long as all wiring is short). For 25 LEDs you only need 4 shift registers.

wires will be long, one led at one meter. 595 will be at every 8 led + transistor for driving led. All this will be in transparent tube and immerse in swimming pool.
Is there another way to control this 25 led's, maybe with even less wires from tube to controller with arduino

You will likely have trouble sending clock and data along long cables like that unless at a low data rate. Logic signals degrade over a few feet / metres and can lead to crosstalk, spurious glitches etc (remember these signals have rise and fall times of a few nanoseconds). I'd select quite a low clock frequency in the first instance, say 10kHz or so, and add 100 ohm resistors in-line before the inputs to each 595 (suppresses reflections). You may still have problems - experiment with one '595 and set of LEDs first.

More advanced cures are adding an RC low-pass filter and a schmitt trigger gate to clean up the edges.

MarkT:
You will likely have trouble sending clock and data along long cables like that unless at a low data rate. Logic signals degrade over a few feet / metres and can lead to crosstalk, spurious glitches etc (remember these signals have rise and fall times of a few nanoseconds). I'd select quite a low clock frequency in the first instance, say 10kHz or so, and add 100 ohm resistors in-line before the inputs to each 595 (suppresses reflections). You may still have problems - experiment with one '595 and set of LEDs first.

More advanced cures are adding an RC low-pass filter and a schmitt trigger gate to clean up the edges.

I still have trouble to make more than 16 leds to move. This is first problem :frowning:
Second, there is a possible problem with a long wires. :frowning:
Is there another way beside 595 to control 25 leds with just few wires? somebody mentioned SPI control

SPI is just another serial clocked protocol, same issues. Some of the LED driver chips have schmitt trigger clock inputs specifically to help with long signal runs. You are using good decoupling aren't you? 22uF or more at each shift register is a start.

There is Charlieplexing - 25 LEDs would take 6 wires and 6 resistors, but you get a reduction in brightness due to multiplexing.

MarkT:
SPI is just another serial clocked protocol, same issues. Some of the LED driver chips have schmitt trigger clock inputs specifically to help with long signal runs. You are using good decoupling aren't you? 22uF or more at each shift register is a start.

There is Charlieplexing - 25 LEDs would take 6 wires and 6 resistors, but you get a reduction in brightness due to multiplexing.

For now all is on breadboard so I don't use any decoupling for now. First I want to make all 25 led running as I expect. After that I will be making a long version and solve problems.
Charlieplexing use too many pins from arduino and it is complicated to cross wires in the tube.

I think you want a little bit of logic at each LED.
Have a little 8-pin uC every meter to control the LED and minimizethe wiring in the tube.

I'd select quite a low clock frequency in the first instance

CrossRoads:
I think you want a little bit of logic at each LED.
Have a little 8-pin uC every meter to control the LED and minimizethe wiring in the tube.

This is possible solution if 595 failed. But this will cost a much more than 4 595 chips + lots of wire, so I will firs try cheaper solution. Thank for your advice and time! :slight_smile:

stanfidavid:
I'd select quite a low clock frequency in the first instance

how to do that?

First I want to make all 25 led running as I expect.

You simply shift out 4 bytes. Using shiftOut() for example:

  shiftOut(data[3]); //shift out the furtherest byte
  shiftOut(data[2]);
  shiftOut(data[1]);
  shiftOut(data[0]); //shift out the closest byte
  //done!

After that I will be making a long version

You can either slow it down or you can use buffers.

Both are very simple.

dhenry:
You can either slow it down or you can use buffers.

Both are very simple.

can you direct me how? with some link maybe?

If you are using hardware spi, you can change the clock rate.

If you are using software spi, you can insert delays, like this:

#define spi_delay()  {NOP(); NOP(); NOP(); NOP(); NOP();} //insert your delay here. example uses 5 nop instructions

void myshiftOut(uint8_t dataPin, uint8_t clockPin, uint8_t bitOrder, uint8_t val)
{
	uint8_t i;

	for (i = 0; i < 8; i++)  {
		digitalWrite(clockPin, LOW);		
                spi_delay(); //insert delay
		if (bitOrder == LSBFIRST)
			digitalWrite(dataPin, !!(val & (1 << i)));
		else	
			digitalWrite(dataPin, !!(val & (1 << (7 - i))));
			
                spi_delay(); //insert delay
		digitalWrite(clockPin, HIGH);
                spi_delay(); //insert delay
	}
}[/core]

By changing the delay you use, you can slow down myshiftOut() as much as you want.

You guys are getting carried away on th clock rates.
You've got 25 LEDs a meter apart going down the length of a swimming pool, they pace a swimmer and don't get updated all that quick.