Урок ESP8266. Подключение сдвигового регистра 74HC595.

Разработка проектов под заказ

Цель этого урока - объяснить, как подключить 8-битный сдвиговый регистр 74HC595 к ESP8266 для управления светодиодами. Также рассмотрим код позволяющий осуществлять управление сдвиговым регистром. Как настроить работу с платой ESP8266 в среде Arduino IDE, описано здесь.

Также у меня есть урок по подключению сдвигового регистра 74HC595 к Arduino, подробнее читайте тут.

Описание сдвигового регистра 74HC595.

Перед тем как собирать схему и писать код нужно разобраться, что такое сдвиговый регистр и как его подключить.

74HC595 — восьмиразрядный (это означает, что он имеет 8 управляемых выходов) с последовательным вводом, последовательным или параллельным выводом информации, с триггером-защелкой.

Описание сдвигового регистра 74HC595

Описание контактов сдвигового регистра 74HC595.

Как видим, сдвиговый регистр подключается по 3 пинам, а к нему можно подключить 8 светодиодов. Также управлять можно не только светодиодами, но и реле, драйверами,транзисторами и тд.

Для проверки работоспособности предположим, что нужно управлять тремя светодиодами, но можно использовать и другое количество, позднее рассмотрим подключение 8 светодиодов. Номинал резисторов может отличаться для разных подключаемых устройств, потому что они должны быть рассчитаны в соответствии с потребляемым током используемых устройств. В Интернете есть множество руководств и инструкций о том, как рассчитать значения резисторов.

Просто убедитесь, что ток не превышает максимальный 35 мА на выходной контакт и максимальный общий ток 70 мА. Данные значения можете проверить в даташите сдвигового регистра 74HC595.

Описание контактов сдвигового регистра 74HC595.

Для управления устройством нам понадобится всего 3 контакта микроконтроллера. В этом случае используем GPIO12 ESP8266 в качестве вывода данных, который подключен к выводу DS или SER интегральной схемы.

Тактовая частота регистра управляется GPIO15 и подключена к выводу SH_Cp или SCK. Передача данных между регистром сдвига и регистром хранения 75HC595 управляется GPIO13, который подключен к выводу ST_CP или RCK.

Вывод OE напрямую подключен к GND, для того чтобы выводы Q0 – Q7 были активны все время, а MR подключен к VCC, потому что не хотим очищать регистр сдвига с помощью управляемого сигнала.

Поскольку мы не объединяем несколько микросхем 75HC595 в цепочку, контакт OE можно оставить неподключенным.

Важно: если вы используете NodeMCU, не забывайте, что номера контактов на плате не соответствуют GPIO ESP8266. Как показано ниже, отображение будет следующим:

  • GPIO15 - контакт D8 NodeMCU
  • GPIO13 - контакт D7 NodeMCU
  • GPIO12 - контакт D6 NodeMCU

Схема подключения сдвигового регистра 74HC595 к NodeMCU.

Для простоты подключения в уроке будем использовать плату NodeMCU. Подключим сдвиговый регистр к 74HC595 к NodeMCU по схеме.

Схема подключения сдвигового регистра 74HC595 к NodeMCU.

Как видим, у нас используется всего 3 контакта NodeMCU для подключения сдвигового регистра, а на выходе управляем 8 светодиодами. Что позволяет расширить возможности ESP8266.

Основные настройки для работы с сдвиговым регистром.

Как объяснялось ранее, нам понадобятся всего 3 контакта ESP8266 для управления 74HC595. Объявим их как глобальные переменные, а затем инициализируем их как выходные контакты в функции настройки setup().

int dataPin = D6; //Пин подключен к DS входу 74HC595
int latchPin = D7; //Пин подключен к ST_CP входу 74HC595
int clockPin = D8; //Пин подключен к SH_CP входу 74HC595
void setup() { //устанавливаем режим OUTPUT
  pinMode(latchPin, OUTPUT);
  pinMode(clockPin, OUTPUT);
  pinMode(dataPin, OUTPUT);
}

Еще один плюс это то, что использование сдвигового регистра достаточно простое и управлять им можно без использования сторонних библиотек.

Управление сдвиговым регистром 74HC595 при помощи NodeMCU.

Поскольку проще работать с отдельными битами, самый простой и менее подверженный ошибкам подход - это указывать данные побитно. Итак, объявим передаваемый байт в двоичном формате. Узнать подробнее о переменной типа byte можно тут. В этом случае мы включим первый светодиод.

byte data = B00000001;    // B00000001, B00000010, B00000100,B00001000, ...

Также можно указать данные в числовом формате, просто вместо байта укажем целое число.

data = 2; //B00000010;
int integerData = 3; //B00000011;

Если хотим следовать этому подходу, мы можем использовать преобразователь двоичных чисел в целые числа, такой как показан здесь.

Если же просто хотим включать по одному светодиоду за раз и не хотим беспокоиться о преобразовании двоичного кода в десятичное, мы можем просто использовать функцию bitWrite(). По сути, она позволяет установить значение (HIGH или LOW) определенного бита.

byte bitSpecified = 0;
int bitNumber = 2;
bitWrite (bitSpecified, bitNumber, HIGH);

В этом случае мы записываем значение HIGH (которое соответствует значению 1) в третий бит переменной (младший бит - это бит 0), что будет соответствовать B00000100.

После установки данных для передачи и перед началом фактического обмена данными мы убедимся, что контакт нагрузки, который запускает передачу данных между внутренними регистрами интегральной схемы, находится в состоянии LOW. Таким образом, мы гарантируем, что передача не произойдет, когда мы отправим 8 бит с микроконтроллера.

digitalWrite (loadPin, LOW); // устанавливаем синхронизацию "защелки" на LOW

Затем мы позаботимся о фактической передаче данных на устройство. Самый простой способ связи со сдвиговым регистром - использовать функцию shiftOut от Arduino.

Эта функция позволяет задавать байт данных (8 бит) побитно. Чтобы достичь этого, каждый бит (представленный сигналом HIGH или LOW) записывается по очереди на ранее указанный вывод, после чего на тактовый вывод подается импульс (принимается HIGH, а затем LOW).

Благодаря этому мы можем легко реализовать процесс загрузки 8 битов в сдвиговый регистр 74HC595. Вызов функции указан ниже.

shiftOut(dataPin, clockPin, MSBFIRST, data); //Инвертируем сигнал при помощи MSBFIRST, грузим с первого бита

Первый аргумент соответствует контакту, на который мы будем передавать данные. Таким образом, именно цифровой вывод микроконтроллера будет подключен к выводу DS интегральной схемы.

Второй аргумент соответствует контакту микроконтроллера, который будет генерировать тактовый сигнал для управления передачей данных на 74HC595.

Третий аргумент указывает, в каком порядке сдвигать биты. В этом случае значение MSBFIRST указывает, что он начнется с самого старшего бита. В качестве альтернативы мы можем передать значение LSBFIRST, которое соответствует наименьшему значению первого бита.

Четвертый и последний аргумент соответствует байту данных, который мы хотим переместить.

После передачи всего байта в 74HC595 мы хотим запустить внутренний перенос из сдвигового регистра интегральной схемы в регистр хранения, чтобы биты были доступны на его выходных контактах. Для этого мы просто меняем значение контакта защелки на HIGH.

digitalWrite(latchPin, HIGH); //"защелкиваем" регистр, тем самым устанавливая значения на выходах

Последний пример управления 3 светодиодами с помощью сдвигового регистра приведен ниже.

void loop() {
  byte data = B00000001;    // B00000001, B00000010, B00000100,B00001000, ... 
  digitalWrite(latchPin, LOW);// устанавливаем синхронизацию "защелки" на LOW
  shiftOut(dataPin, clockPin, MSBFIRST, data);// Инвертируем сигнал при помощи MSBFIRST, грузим с первого бита
  digitalWrite(latchPin, HIGH); //"защелкиваем" регистр, тем самым устанавливая значения на выходах
  delay(1000);
  data = 2; //B00000010;
  digitalWrite(latchPin, LOW);
  shiftOut(dataPin, clockPin, MSBFIRST, data);
  digitalWrite(latchPin, HIGH);
  delay(1000);
  int integerData = 3; //B00000011;
  digitalWrite(latchPin, LOW);
  shiftOut(dataPin, clockPin, MSBFIRST, integerData);
  digitalWrite(latchPin, HIGH);
  delay(1000);
  byte bitSpecified = 0;
  int bitNumber = 2;
  bitWrite(bitSpecified, bitNumber, HIGH); // При bitPos=0 получим B00000001, при bitPos=1 - B00000010, при bitPos=2 - B00000100 и т.д. 
  digitalWrite(latchPin, LOW);
  shiftOut(dataPin, clockPin, MSBFIRST, bitSpecified);
  digitalWrite(latchPin, HIGH);
  delay(1000);
  data = 0;
  digitalWrite(latchPin, LOW);
  shiftOut(dataPin, clockPin, MSBFIRST, data);
  digitalWrite(latchPin, HIGH);
  delay(1000);
}

В коде мы предаём следующие данные в сдвиговый регистр:

  • Первый светодиод горит (B00000001)
  • Второй светодиод горит (B00000010)
  • Горят первый и второй светодиоды (B00000011)
  • Горит третий светодиод (B00000100)
  • Все светодиоды выключены (B00000000)

Пример бегущих огней на сдвиговом регистре 74HC595 и NodeMCU.

Схема подключения остается такой же, как и в предыдущем примере.

Пример бегущих огней на сдвиговом регистре 74HC595 и NodeMCU.

Используя полученные знания, дополним предыдущий пример, в котором передавать значения будем в цикле, поочерёдно включая светодиоды, друг за другом.

int dataPin = D6; //Пин подключен к DS входу 74HC595 
int latchPin = D7; //Пин подключен к ST_CP входу 74HC595 
int clockPin = D8; //Пин подключен к SH_CP входу 74HC595
void setup() { //устанавливаем режим OUTPUT 
  pinMode(latchPin, OUTPUT); 
  pinMode(clockPin, OUTPUT);
  pinMode(dataPin, OUTPUT); 
} 
void loop() { 
  byte byteToSend = 0; //Создаем пустой байт B00000000 
  for (int bitPos = 0; bitPos < 8; bitPos++) { // В переменной хранится позиция изменяемого бита 
    byteToSend = 0; // Обнуляем байт при каждом проходе 
    bitWrite(byteToSend, bitPos, HIGH); // При bitPos=0 получим B00000001, при bitPos=1 - B00000010, при bitPos=2 - B00000100 и т.д. 
    digitalWrite(latchPin, LOW);  // устанавливаем синхронизацию "защелки" на LOW
    shiftOut(dataPin, clockPin, LSBFIRST, byteToSend); // Инвертируем сигнал при помощи MSBFIRST, грузим с первого бита 
    digitalWrite(latchPin, HIGH); //"защелкиваем" регистр, тем самым устанавливая значения на выходах
    delay(150); 
  } 
  for (int bitPos = 0; bitPos < 8; bitPos++) { // В переменной хранится позиция изменяемого бита 
    byteToSend = 0; // Обнуляем байт при каждом проходе 
    bitWrite(byteToSend, bitPos, HIGH); // При bitPos=0 получим B00000001, при bitPos=1 - B00000010, при bitPos=2 - B00000100 и т.д. 
    digitalWrite(latchPin, LOW);  // устанавливаем синхронизацию "защелки" на LOW
    shiftOut(dataPin, clockPin, MSBFIRST, byteToSend); // Инвертируем сигнал при помощи MSBFIRST, грузим с первого бита 
    digitalWrite(latchPin, HIGH); //"защелкиваем" регистр, тем самым устанавливая значения на выходах
    delay(150); 
  } 
}

Во втором цикле будем включать светодиоды в обратном порядке. В этом нам поможет изменение значение LSBFIRST на MSBFIRST.

int dataPin = D6; //Пин подключен к DS входу 74HC595 
int latchPin = D7; //Пин подключен к ST_CP входу 74HC595 
int clockPin = D8; //Пин подключен к SH_CP входу 74HC595
void setup() { //устанавливаем режим OUTPUT 
  pinMode(latchPin, OUTPUT); 
  pinMode(clockPin, OUTPUT);
  pinMode(dataPin, OUTPUT); 
} 
void loop() { 
  byte byteToSend = 0; //Создаем пустой байт B00000000 
  for (int bitPos = 0; bitPos < 8; bitPos++) { // В переменной хранится позиция изменяемого бита 
    //byteToSend = 0; // Обнуляем байт при каждом проходе 
    bitWrite(byteToSend, bitPos, HIGH); // При bitPos=0 получим B00000001, при bitPos=1 - B00000011, при bitPos=2 - B00000100 и т.д. 
    digitalWrite(latchPin, LOW);  // устанавливаем синхронизацию "защелки" на LOW
    shiftOut(dataPin, clockPin, LSBFIRST, byteToSend); // Инвертируем сигнал при помощи MSBFIRST, грузим с первого бита 
    digitalWrite(latchPin, HIGH); //"защелкиваем" регистр, тем самым устанавливая значения на выходах
    delay(150); 
  } 
  for (int bitPos = 0; bitPos < 8; bitPos++) { // В переменной хранится позиция изменяемого бита 
    //byteToSend = 0; // Обнуляем байт при каждом проходе 
    bitWrite(byteToSend, bitPos, LOW); // При bitPos=0 получим B11111110, при bitPos=1 - B11111100, при bitPos=2 - B11111000 и т.д. 
    digitalWrite(latchPin, LOW);  // устанавливаем синхронизацию "защелки" на LOW
    shiftOut(dataPin, clockPin, MSBFIRST, byteToSend); // Инвертируем сигнал при помощи MSBFIRST, грузим с первого бита 
    digitalWrite(latchPin, HIGH); //"защелкиваем" регистр, тем самым устанавливая значения на выходах
    delay(150); 
  } 
}

Пример 2 бегущие огни на сдвиговом регистре 74HC595 и NodeMCU.

На основе данного примера можно реализовать различные варианты бегущих огней. К примеру, такой вариант, который позволяет включить все светодиоды по одному и при обратном проходе выключить их также по очереди.

Вывод.

Как видим сдвиговый регистр достаточно простой в использовании и его можно использовать, когда у нас не хватает пинов на плате ESP8266 (NodeMCU).

Понравился Урок ESP8266.Подключение сдвигового регистра 74HC595? Не забудь поделиться с друзьями в соц. сетях.

А также подписаться на наш канал на YouTube, вступить в группу Вконтакте, в группу на Facebook.

Спасибо за внимание!

Технологии начинаются с простого!

Фотографии к статье

Файлы для скачивания

Простой пример кода включения светодиодов при помощи сдвигового регистра и NodeMCU Простой пример кода включения светодиодов при помощи сдвигового регистра и NodeMCU.ino2 Kb 14 Скачать
Пример бегущих огней на сдвиговом регистре 74HC595  и NodeMCU Пример бегущих огней на сдвиговом регистре 74HC595 и NodeMCU.ino2 Kb 8 Скачать
Пример 2. бегущие огни на сдвиговом регистре 74HC595  и NodeMCU Пример 2. бегущие огни на сдвиговом регистре 74HC595 и NodeMCU.ino2 Kb 8 Скачать

Комментарии

Ваше Имя*