// A - очистка ввода кода
// B - удаление последней цифры
// C - подтверждение ввода

#include <Keypad.h>
#include <LiquidCrystal_I2C.h>;       //  Подключаем библиотеку для работы с LCD дисплеем по шине I2C
#include <Servo.h>; 

const byte ROWS = 4;
const byte COLS = 4;
byte time=0, timeOpen=0, CodeOk=0, inv=1, newCode=0;
String myCode="";
String myEnterCode="";

char keys[ROWS][COLS] = {
  { '1', '2', '3', 'A' },
  { '4', '5', '6', 'B' },
  { '7', '8', '9', 'C' },
  { '*', '0', '#', 'D' }
};

uint8_t rowPins[ROWS] = { 9, 8, 7, 6 }; // Pins connected to R1, R2, R3, R4
uint8_t colPins[COLS] = { 5, 4, 3, 2 }; // Pins connected to C1, C2, C3, C4

Keypad keypad = Keypad(makeKeymap(keys), rowPins, colPins, ROWS, COLS);
LiquidCrystal_I2C lcd(0x27, 16, 2);       //  Объявляем  объект библиотеки, указывая параметры дисплея (адрес I2C = 0x27, количество столбцов = 16, количество строк = 2)
Servo servo;

void setup() {
  Serial.begin(9600);
  lcd.init();  
  lcd.setCursor(0, 0); 
  lcd.backlight();
  servo.attach(10);
  servo.write(0);
}

void loop() 
{
  // if (inv==1){
  //   lcd.setCursor(myCode.length(), 1);
  //   lcd.print("_");
  //   inv=inv*(-1);
  // } else {
  //   lcd.setCursor(myCode.length(), 1);
  //   lcd.print(" ");
  //   inv=inv*(-1);
  // }
  delay(100);
  char key = keypad.getKey();
  if (newCode==0)
  {
    Rows(0,0, "Enter new code");

    myEnterCode=EnterKey(key, myEnterCode);
    
    myEnterCode=EnterKeyA(key,myCode);
    //if (key=='A')
    //{
      //Rows(0,1,"             ");
      //myEnterCode="";
    //}
   myEnterCode=EnterKeyB(key,myCode);
  

 if (key=='C')
    {
      newCode=1;
      Rows(0,0,"Enter code        ");
      Rows(0,1,"             ");
    }
}
    else 
    {
      if (time==0)
      {
        lcd.noBacklight();
      }    
      if (myCode.length()==0)
      {
        lcd.backlight();
      }   
      myEnterCode=EnterKeyA(key,myCode);
      //if (key=='A')
      //{
        //Rows(0,1,"             ");
        //myCode="";
      //}
      
      myEnterCode=EnterKeyB(key,myCode);



      //if ((key=='B')&&(myCode.length()>0)){
        //Rows(0,1,"             ");
        //myCode=myCode.substring(0,(myCode.length()-1));
        //Rows(0,1,myCode);
        //Serial.print("myCode=");
        //Serial.println(myCode);
        //}
     
      if (key=='C')
      {
        if (myCode==myEnterCode)
        {
          servo.write(180);
          Rows(1,1,"CODE OK");
            
          myCode="";
          time=0;
          CodeOk=1;
        } 
          else 
          {
            Rows(0,1,"             ");
            myCode="";
            myCode="";
            time=0;
          }
        Serial.print("myCode=");
        Serial.println(myCode);
      }
      if (myCode.length()>0)
      {
        time++;
        Serial.print("Time=");
        Serial.println(time);
      }
      if (time>250)
      {
        Rows(0,1,"             ");
        lcd.noBacklight();
        myCode="";
        time=0; 
      }
      if (CodeOk==1)
      {
        timeOpen++;
      }
      if (timeOpen>50)
      {
        Rows(0,1,"             ");
        lcd.noBacklight();
        CodeOk=0;
        timeOpen=0; 
      }
   }
  }
void Rows(byte columnNumber, byte rowsNumber, String OneRowsString)
{
  lcd.setCursor(columnNumber, rowsNumber);    
  lcd.print(OneRowsString);
}

String EnterKey (char enterKey, String enterString)
{
  if ((enterKey != NO_KEY)&&((enterString.length())<16)&&(enterKey>='0')&&(enterKey<='9')) 
  {
      enterString=enterString+enterKey;
      Rows(0,1,enterString);
      Serial.println(enterString);
  }
  return enterString;
}
String EnterKeyB (char enterKey, String enterString)
{
 if ((enterKey=='B')&&(enterString.length()>0))
 {
  Rows(0,1,"             ");
  enterString=enterString.substring(0,(enterString.length()-1));
  Rows(0,1,enterString);

}
  return enterString;
}

String EnterKeyA (char enterKey, String enterString)
{
  if (enterKey=='A')
    {
      Rows(0,1,"             ");
      myEnterCode="";
    }
  return enterString;
}