#include <Mtk74HC595.h>
#include <Mtk74HC165.h>

////////////////////////////////////////////////////////////
// Увеличение выходных пинов с помощью микросхемы 74HC595 //
// http://codius.ru/articles/Arduino_%D0%A1%D0%B4%D0%B2%D0%B8%D0%B3%D0%BE%D0%B2%D1%8B%D0%B9_%D1%80%D0%B5%D0%B3%D0%B8%D1%81%D1%82%D1%80_74%D0%9D%D0%A1595_%D0%B8%D0%BB%D0%B8_%D1%80%D0%B0%D0%B7%D0%BC%D0%BD%D0%BE%D0%B6%D0%B0%D0%B5%D0%BC_%D1%8D%D0%BA%D0%BE%D0%BD%D0%BE%D0%BC%D0%B8%D0%BC_%D0%B2%D1%8B%D1%85%D0%BE%D0%B4%D1%8B_%D0%BF%D0%BB%D0%B0%D1%82%D1%8B
// Увеличение входных пинов с помощью микросхемы 74HC165  //
// https://wokwi.com/projects/306024460940476993
// https://wokwi.com/projects/372318192577515521
////////////////////////////////////////////////////////////

#define MTK__PIN_OUT__LED 2

//----------------------------------------------------------
// Пины микросхемы 74HC595 - ВЫХОДНОЙ РЕГИСТР
#define PIN_OUT__MPX_595_DATA   5 // к выводу 14 регистра (DS)
#define PIN_OUT__MPX_595_CLOCK 19 // к выводу 11 регистра (SH_CP)
#define PIN_OUT__MPX_595_LATCH 18 // к выводу 12 регистра (ST_CP)
#define PIN_OUT__MPX_595_OE    17 // к выводу 13 регистра (OE) // В ТЕОРИИ МОЖНО И БЕЗ НЕГО УПРАВЛЯТЬ!

Mtk74HC595 pinOUT(PIN_OUT__MPX_595_DATA, PIN_OUT__MPX_595_CLOCK, PIN_OUT__MPX_595_LATCH, PIN_OUT__MPX_595_OE);
uint8_t outPines[16] {
  pinOUT.PIN1, pinOUT.PIN2, pinOUT.PIN3, pinOUT.PIN4,
  pinOUT.PIN5, pinOUT.PIN6, pinOUT.PIN7, pinOUT.PIN8,
  pinOUT.PIN9, pinOUT.PIN10, pinOUT.PIN11, pinOUT.PIN12,
  pinOUT.PIN13, pinOUT.PIN14, pinOUT.PIN15, pinOUT.PIN16
};
//----------------------------------------------------------

//----------------------------------------------------------
// Пины микросхемы 74HC165 - ВХОДНОЙ РЕГИСТР
#define PIN_OUT__MPX_165_DATA  21 // к выводу 9 регистра (Q7)
#define PIN_OUT__MPX_165_CLOCK 22 // к выводу 2 регистра (CP)
#define PIN_OUT__MPX_165_LATCH 23 // к выводу 1 регистра (PL)

Mtk74HC165 pinIN(PIN_OUT__MPX_165_DATA, PIN_OUT__MPX_165_CLOCK, PIN_OUT__MPX_165_LATCH);
uint8_t inPines[16] {
  pinIN.PIN1, pinIN.PIN2, pinIN.PIN3, pinIN.PIN4,
  pinIN.PIN5, pinIN.PIN6, pinIN.PIN7, pinIN.PIN8,
  pinIN.PIN9, pinIN.PIN10, pinIN.PIN11, pinIN.PIN12,
  pinIN.PIN13, pinIN.PIN14, pinIN.PIN15, pinIN.PIN16
};
//----------------------------------------------------------



void setup()
{
  Serial.begin(9600);

  Serial.println("Init...");
  pinOUT.init();
  pinIN.init();
  Serial.println("Started");
}

void loop()
{
  /// ВЫХОДНЫЕ ПИНЫ

  static int pause = 500;

  /*
    // Бегущий огонь - слева на право
    for (int i = 0; i < 16; i++) {
    pinOUT.write(outPines[i], HIGH);
    delay(pause);
    pinOUT.write(outPines[i], LOW);
    }
  */

  /*
    // Бегущий огонь - оба навстречу
    for (int i = 0; i < 16; i++) {
    pinOUT.write(outPines[i], HIGH);
    pinOUT.write(outPines[15 - i], HIGH);
    delay(pause);
    pinOUT.write(outPines[i], LOW);
    pinOUT.write(outPines[15 - i], LOW);
    }
  */

  /*
  /// ВХОДНЫЕ ПИНЫ (опрос 16 пинов занимает 8мсек)
  while (1 == 1) {
    //long m = millis();
    pinIN.readAll();
    for (int i = 0; i < 16; i++) {
      pinOUT.write(outPines[i], pinIN.read(inPines[i]));
    }
    //Serial.println(String(millis()-m));
  }
  */

  pause = 50;

  pinOUT.reset();

  // Бегущий огонь - туда/сюда
  for (int i = 0; i < 16; i++)
  {
    pinOUT.write(outPines[i], HIGH);
    delay(pause);
    pinOUT.write(outPines[i], LOW);
  }
  for (int i = 15; i > 0; i--)
  {
    pinOUT.write(outPines[i], HIGH);
    delay(pause);
    pinOUT.write(outPines[i], LOW);
  }

  pinOUT.reset();

  for (int i = 0; i < 16; i++)
  {
    pinOUT.write(outPines[i], HIGH);
    delay(pause);
  }

  delay(100);

  //for (int i = 15; i > 0; i++)
  for (int i = 0; i < 16; i++)
  {
    pinOUT.write(outPines[i], LOW);
    delay(pause);
  }

  delay(100);

  //pinOUT.write(pinOUT.PIN1, HIGH);
  //delay(100);
  //pinOUT.write(pinOUT.PIN1, LOW);

  //delay(250);
}
74HC595
74HC595
74HC165
74HC165
NOCOMNCVCCGNDINLED1PWRRelay Module