C贸mo funciona el registro de turnos 74HC595 y su interfaz con Arduino

驴Qu茅 es el 74HC595?

驴Alguna vez te has encontrado queriendo controlar muchos LEDs? 驴O s贸lo necesitabas m谩s pines de E/S para controlar botones, sensores, servos, todo a la vez? Bueno, podr铆as conectar unos cuantos sensores a los pines de Arduino, pero r谩pidamente te quedar铆as sin pines en tu placa.

La soluci贸n para esto es usar un 芦Registro de turnos禄. Un registro de desplazamiento te permite ampliar el n煤mero de pines de E/S que puedes utilizar de tu Arduino (o cualquier microcontrolador para el caso). Y el registro de desplazamiento 74HC595 (apodado ‘595’) es uno de los m谩s famosos entre todos.

El 595 controla esencialmente ocho pines de salida separados, usando s贸lo tres pines de entrada. Y si necesitas m谩s de 8 l铆neas de E/S adicionales, puedes encadenar f谩cilmente tantos registros de desplazamiento como quieras y crear toneladas de l铆neas de E/S. Todo esto se logra mediante lo que se conoce como 芦bit-shifting禄. Si quieres saber m谩s sobre el cambio de bits, en esta entrada de la Wikipedia te lo explican perfectamente.

Piezas/pcs. 5 x 74HC595 con/with DIP16 Z贸calo/Socket 8-bit Shift...
  • 5 Piezas/pcs. x 74HC595 con/with DIP16 Sockel/Socket
  • 8-BIT SHIFT REGISTER
  • Autentico / Genuine Texas Instruments

驴Cu谩ndo usar el Registro de turnos?

Los registros de turnos se utilizan a menudo con el fin de guardar los pines del microcontrolador, ya que cada microcontrolador tiene un n煤mero limitado de pines de E/S (GPIO).

Si tu proyecto necesita controlar 16 LEDs individuales, eso normalmente requerir铆a 16 pines de un Arduino. En el caso de que no tengas 16 pines de E/S disponibles, aqu铆 es donde el registro de desplazamiento es 煤til y entra en juego. Con dos registros de cambio conectados en serie, podemos realizar la tarea de controlar los 16 LEDs con s贸lo 3 pines de E/S. Y no s贸lo esto; puedes guardar m谩s pines cuanto m谩s registros de desplazamiento tengas encadenados.

Un ejemplo del mundo real que utiliza el registro de desplazamiento es el 芦Mando Original de Nintendo禄. El mando principal de la Nintendo Entertainment System necesitaba que se pulsaran todos los botones en serie, y utilizaba un registro de desplazamiento para realizar esa tarea.

SIPO contra los registros de turno PISO

Los registros de desplazamiento vienen en dos tipos b谩sicos, o bien SIPO (Serial-In-Parallel-Out) o PISO (Parallel-In-Serial-Out). El popular chip SIPO es 74HC595, y el chip PISO es 74HC165.

El primer tipo, SIPO, es 煤til para controlar un gran n煤mero de salidas, como los LEDs. Mientras que el segundo tipo, PISO, es bueno para reunir un gran n煤mero de entradas, como botones; como el que se utiliza en el mando original de Nintendo como se ha mencionado anteriormente.

驴C贸mo funciona el registro de turnos 74HC595?

El 595 tiene dos registros (que se pueden considerar como 芦contenedores de memoria禄), cada uno con s贸lo 8 bits de datos. El primero se llama Registro de Turno. El Registro de Turno se encuentra en lo profundo de los circuitos IC, aceptando silenciosamente la entrada.

Cada vez que aplicamos un pulso de reloj a un 595, ocurren dos cosas:

Los bits del Registro de Turnos se mueven un paso a la izquierda. Por ejemplo, el bit 7 acepta el valor que antes estaba en el bit 6, el bit 6 obtiene el valor del bit 5, etc.
El bit 0 del Registro de Turnos acepta el valor actual en el pin DATA. En el borde ascendente del pulso, si el pin de datos es alto, entonces un 1 se empuja en el registro de desplazamiento. De lo contrario, es un 0.

Al activar la clavija Latch, el contenido del Registro de Desplazamientos se copia en el segundo registro, llamado Registro de Almacenamiento/Latch. Cada bit del Registro de almacenamiento est谩 conectado a uno de los pines de salida QA-QH del IC, as铆 que en general, cuando el valor del Registro de almacenamiento cambia, tambi茅n lo hacen las salidas.

74HC595 Pinout

El 595 viene en una variedad de marcas y modelos; aqu铆 hablaremos del omnipresente Texas Instruments SN74HC595N. Si tienes uno diferente, estudia su hoja de datos cuidadosamente y toma nota de cualquier diferencia.

Echemos un vistazo a su Pinout. F铆jate que dos pines tienen una l铆nea sobre su nombre; esto significa que operan en 芦l贸gica negativa禄. Lo sabr谩s un poco m谩s tarde.

pinout 74HC595

  • GND deber铆a estar conectado a la tierra de Arduino.
  • VCC es la fuente de alimentaci贸n para el registro de cambio 74HC595 que conectamos al pin 5V de Arduino.
  • El pin SER (Serial Input) se utiliza para alimentar los datos en el registro de cambio de un bit a la vez.
  • SRCLK (Shift Register Clock) es el reloj del registro de cambio. El 595 es impulsado por el reloj en el borde ascendente. Esto significa que para desplazar bits en el registro de desplazamiento, el reloj debe estar ALTO (HIGH). Y los bits se transfieren en el borde ascendente del reloj.
  • RCLK (Register Clock / Latch) es un pin muy importante. Cuando se maneja en ALTO (HIGH), el contenido del Registro de Desplazamiento se copia en el Registro de Almacenamiento / Reloj; que finalmente se muestra en la salida. As铆 que la clavija del pestillo puede ser vista como el paso final en el proceso de ver nuestros resultados en la salida, que en este caso son los LEDs.
  • La clavija SRCLR (Shift Register Clear) nos permite reiniciar todo el Registro de Desplazamiento, haciendo que todos sus bits sean 0, a la vez. Este es un pin de l贸gica negativa, as铆 que para realizar este restablecimiento, necesitamos poner el pin SRCLR en LOW. Cuando no se requiere un restablecimiento, este pin debe ser ALTO (HIGH).
  • OE (Output Enable) tambi茅n es de l贸gica negativa: Cuando el voltaje en 茅l es ALTO聽(HIGH), los pines de salida se deshabilitan/se ajustan a un estado de alta impedancia y no permiten que la corriente fluya. Cuando OE tiene bajo voltaje, los pines de salida funcionan normalmente.
  • QA-QH (Output Enable) son los pines de salida y deben ser conectados a alg煤n tipo de salida como LEDs, 7 segmentos, etc.
  • El Pin ‘QH’ da salida al bit 7 del ShiftRegister. Est谩 ah铆 para que podamos encadenar 595s: si conectas este QH’ al pin SER de otro 595, y das a ambos ICs la misma se帽al de reloj, se comportar谩n como un solo IC con 16 salidas. Por supuesto, esta t茅cnica no est谩 limitada a dos ICs, puedes encadenar tantos como quieras, si tienes suficiente potencia para todos ellos.

Cableado y Conexi贸n del registro de turnos 74HC595 a Arduino UNO

Ahora que tenemos un conocimiento b谩sico de c贸mo funciona 74HC595, podemos empezar a conectarlo a nuestro Arduino.

Empieza colocando el registro de cambio en tu tablero, asegur谩ndote de que cada lado del CI est茅 en un lado separado del tablero. Con la peque帽a muesca en forma de U mirando hacia arriba, los pines est谩n 1-8 abajo del lado izquierdo de arriba a abajo y 16 – 9 abajo del lado derecho de arriba a abajo como se puede ver en la ilustraci贸n de abajo.

Para empezar, conectemos las clavijas 16 (VCC) y 10 (SRCLR) a la clavija 5v del Arduino y conectemos las clavijas 8 (GND) y 13 (OE) a la clavija Gnd del Arduino. Esto deber铆a mantener el CI en el modo de trabajo normal.

A continuaci贸n tenemos que conectar los tres pines con los que controlaremos el registro de cambio:

  • El pin 11 (SRCLK) del registro de cambio al pin 6 del Arduino
  • El pin 12 (RCLK) del registro de cambio al pin 5 en el Arduino
  • El pin 14 (SER) del registro de cambio al pin 4 en el Arduino

Ahora, s贸lo tenemos que conectar todos los pines de salida a nuestros LEDs, asegur谩ndonos de que una resistencia 220惟 se coloca antes de los LEDs para reducir la corriente y que los c谩todos de los LEDs vuelven a tierra.

Cuando coloques los LEDs aseg煤rate de que est茅n conectados en orden, de modo que QA est茅 conectado al primer LED, y QH est茅 conectado al 煤ltimo LED, ya que de lo contrario nuestro c贸digo no va a encender los LEDs en el orden correcto!

Cuando termines deber铆as tener algo que se vea similar a la ilustraci贸n que se muestra a continuaci贸n.

conexi贸n 74HC595 a Arduino Uno

C贸digo de Arduino

Ahora estamos listos para escribir el c贸digo. Enchufa tu Arduino en tu ordenador y prueba el sketch; y luego lo diseccionaremos con alg煤n detalle.

int latchPin = 5; // Latch pin of 74HC595 is connected to Digital pin 5
int clockPin = 6; // Clock pin of 74HC595 is connected to Digital pin 6
int dataPin = 4; // Data pin of 74HC595 is connected to Digital pin 4

byte leds = 0; // Variable to hold the pattern of which LEDs are currently turned on or off

/*
* setup() - this function runs once when you turn your Arduino on
* We initialize the serial connection with the computer
*/
void setup()
{
// Set all the pins of 74HC595 as OUTPUT
pinMode(latchPin, OUTPUT);
pinMode(dataPin, OUTPUT);
pinMode(clockPin, OUTPUT);
}

/*
* loop() - this function runs over and over again
*/
void loop()
{
leds = 0; // Initially turns all the LEDs off, by giving the variable 'leds' the value 0
updateShiftRegister();
delay(500);
for (int i = 0; i < 8; i++) // Turn all the LEDs ON one by one.
{
bitSet(leds, i); // Set the bit that controls that LED in the variable 'leds'
updateShiftRegister();
delay(500);
}
}

/*
* updateShiftRegister() - This function sets the latchPin to low, then calls the Arduino function 'shiftOut' to shift out contents of variable 'leds' in the shift register before putting the 'latchPin' high again.
*/
void updateShiftRegister()
{
digitalWrite(latchPin, LOW);
shiftOut(dataPin, clockPin, LSBFIRST, leds);
digitalWrite(latchPin, HIGH);
}

 

Una vez que cargues el c贸digo al Arduino, deber铆as ver que los leds se van encendiendo uno a uno.

Si quisieras apagar uno de los LEDs en vez de encenderlo, llamar铆as a una funci贸n similar de Arduino, bitClear() en la variable ‘leds’. Esto pondr谩 ese bit particular de ‘leds’ a 0 y entonces s贸lo necesitar铆as llamar a updateShiftRegister() para actualizar los LEDs reales.

Explicaci贸n del c贸digo:

Lo primero que hacemos es definir los 3 pines de control, es decir, el pin del reloj y el pin de datos del 74HC595, vamos a conectarnos a los pines digitales #5, #6 y #4 de Arduino respectivamente.

int latchPin = 5;
int clockPin = 6;
int dataPin = 4;

 

A continuaci贸n, se define una variable llamada ‘leds’. Esto se usar谩 para mantener el patr贸n de qu茅 LEDs est谩n actualmente encendidos o apagados. Los datos del tipo ‘byte’ representan n煤meros que usan ocho bits. Cada bit puede estar encendido o apagado, as铆 que esto es perfecto para llevar la cuenta de cu谩l de nuestros ocho LEDs est谩n encendidos o apagados.

// Variable to hold the pattern of which LEDs are currently turned on or off
byte leds = 0;

En la funci贸n de 芦configuraci贸n禄: simplemente inicializamos los tres pines para que sean salidas digitales.

void setup()
{
pinMode(latchPin, OUTPUT);
pinMode(dataPin, OUTPUT);
pinMode(clockPin, OUTPUT);
}

La funci贸n de bucle: inicialmente apaga todos los LEDs, poniendo todos los bits de la variable ‘leds’ a 0. Luego llama a la funci贸n personalizada llamada updateShiftRegister() que enviar谩 el patr贸n de ‘leds’ al registro de cambio para que todos los LEDs se apaguen. M谩s adelante veremos c贸mo funciona updateShiftRegister().

El programa se detiene durante medio segundo y luego comienza a contar de 0 a 7 usando el bucle ‘for’ y la variable ‘i’. Cada vez, utiliza la funci贸n de Arduino bitSet() para establecer el bit que controla el LED particular en la variable ‘leds’. Luego tambi茅n llama a updateShiftRegister() para que el estado de los LEDs cambie de acuerdo a lo que hay en la variable ‘leds’.

Entonces hay un retraso de medio segundo antes de que la 芦i禄 se incremente y se encienda el siguiente LED.

void loop()
{
leds = 0;
updateShiftRegister();
delay(500);
for (int i = 0; i < 8; i++)
{
bitSet(leds, i);
updateShiftRegister();
delay(500);
}
}

La funci贸n updateShiftRegister() , en primer lugar pone el pasador del pestillo en LOW, y luego llama a la funci贸n de Arduino shiftOut() antes de poner el pasador del pestillo en HIGH de nuevo.

Afortunadamente Arduino proporciona una funci贸n de ayuda espec铆fica para los registros de cambio llamada shiftOut() , que nos permite simplemente cambiar los bits en una llamada. Puedes explorar m谩s sobre la biblioteca en la p谩gina web oficial de Arduino.

La funci贸n shiftOut() toma cuatro par谩metros; los dos primeros son los pines a utilizar para Data y Clock respectivamente. El tercer par谩metro especifica en qu茅 extremo de los datos quieres empezar. Vamos a empezar con el bit m谩s correcto, que se denomina 芦Bit menos significativo禄 (LSB).

El 煤ltimo par谩metro es el dato real que se desplazar谩 en el registro de desplazamiento, que en este caso es ‘leds’.

void updateShiftRegister()
{
digitalWrite(latchPin, LOW);
shiftOut(dataPin, clockPin, LSBFIRST, leds);
digitalWrite(latchPin, HIGH);
}

 

Control del brillo mediante PWM

Como suplemento, aqu铆 hay otro proyecto, basado en la misma configuraci贸n pero con una peque帽a diferencia, donde manipulamos otra clavija de control en el IC, es decir, el OE – y al hacer eso, podemos controlar el brillo de los LEDs de salida!

Ya hemos aprendido que la clavija OE (Output Enable) act煤a como un interruptor. Cuando esta clavija est谩 en HIGH, las clavijas de salida se desactivan (funciona con l贸gica negativa, 驴recuerdas?). Y cuando OE recibe bajo voltaje, los pines de salida funcionan normalmente.

En nuestro ejemplo anterior, hab铆amos conectado esta clavija permanentemente a Tierra, habilitando las salidas todo el tiempo. Si conectamos esta clavija a cualquiera de los pines digitales de Arduino y programamos para conmutar su estado.

Pero, en lugar de hacer eso, podemos usar esta clavija junto con la funci贸n analogWrite(), para controlar el brillo de los LEDs usando PWM.

Actually the HIGH parts of the PWM signal will still cause the OE pin to temporarily disable all the IC outputs. But, this will happen, of course, faster than our eyes can perceive directly, but we will definitely sense a variation in the overall brightness.

En realidad, las partes HIGH de la se帽al PWM todav铆a causar谩n que el pin OE desactive temporalmente todas las salidas IC. Pero, esto suceder谩, por supuesto, m谩s r谩pido de lo que nuestros ojos pueden percibir directamente, pero definitivamente sentiremos una variaci贸n en el brillo general.

Para hacer esto, todo lo que necesitas hacer, es cambiar la conexi贸n al pin 13 del 74HC595. As铆 que en lugar de conectarlo a la tierra, lo conectas al pin 3 del Arduino.

El siguiente c贸digo hace que una vez que todos los LEDs han sido encendidos se apaguen gradualmente.

int latchPin = 5; // Latch pin of 74HC595 is connected to Digital pin 5
int clockPin = 6; // Clock pin of 74HC595 is connected to Digital pin 6
int dataPin = 4; // Data pin of 74HC595 is connected to Digital pin 4
int outputEnablePin = 3; // OE pin of 74HC595 is connected to PWM pin 3

byte leds = 0; // Variable to hold the pattern of which LEDs are currently turned on or off

/*
* setup() - this function runs once when you turn your Arduino on
* We initialize the serial connection with the computer
*/
void setup()
{
// Set all the pins of 74HC595 as OUTPUT
pinMode(latchPin, OUTPUT);
pinMode(dataPin, OUTPUT);
pinMode(clockPin, OUTPUT);
pinMode(outputEnablePin, OUTPUT);
}

/*
* loop() - this function runs over and over again
*/
void loop()
{
setBrightness(255);
leds = 0; // Initially turns all the LEDs off, by giving the variable 'leds' the value 0
updateShiftRegister();
delay(500);
for (int i = 0; i < 8; i++) // Turn all the LEDs ON one by one.
{
bitSet(leds, i); // Set the bit that controls that LED in the variable 'leds'
updateShiftRegister();
delay(500);
}
for (byte b = 255; b > 0; b--) // Gradually fade all the LEDs back to off
{
setBrightness(b);
delay(50);
}
}

/*
* updateShiftRegister() - This function sets the latchPin to low, then calls the Arduino function 'shiftOut' to shift out contents of variable 'leds' in the shift register before putting the 'latchPin' high again.
*/
void updateShiftRegister()
{
digitalWrite(latchPin, LOW);
shiftOut(dataPin, clockPin, LSBFIRST, leds);
digitalWrite(latchPin, HIGH);
}

/*
* setBrightness() - Generates PWM signal and writes it to OE pin.
*/
void setBrightness(byte brightness) // 0 to 255
{
analogWrite(outputEnablePin, 255-brightness);
}

 

Y entonces los LEDS despu茅s de encenderse se apaguen gradualmente.

Pin It on Pinterest

Shares