What in my code is using so much Dynamic memory?

I have been working on this code for a while now, and i noticed the lcd screen stopped working(stopped displaying anything) after I implimented the IR controller.
It seems to me that dynamic memory is why my lcd stopped working. If i comment out everything relating to the IR controller my program runs fine. please help, thanks<3

#include <LiquidCrystal_I2C.h>
#include <Keypad.h>
#include <RTClib.h>
#include <DHT11.h>
#include <DIYables_IRcontroller.h>

//DESIGNATION OF VALUES-----------------------------------
  //KEYPAD--------------------------------------------------
    const byte ROWS = 4;  //four rows
    const byte COLS = 4;  //four columns
    char hexaKeys[COLS][ROWS] = {
      { '1', '4', '7', '*' },
      { '2', '5', '8', '0' },
      { '3', '6', '9', '#' },
      { 'A', 'B', 'C', 'D' }
    };
    byte rowPins[ROWS] = { 7, 6, 5, 4 };    //connect to the row pinouts of the keypad
    byte colPins[COLS] = { 11, 10, 9, 8 };  //connect to the column pinouts of the keypad
    Keypad customKeypad = Keypad(makeKeymap(hexaKeys), rowPins, colPins, ROWS, COLS);

  //IR CONTROLLER-------------------------------------------
    #define IR_RECEIVER_PIN 3 // connect the IR Receiver to pin 3
    DIYables_IRcontroller_17 irController(IR_RECEIVER_PIN, 200); //debounce time is 200ms
  //LCD-----------------------------------------------------
    LiquidCrystal_I2C lcd(0x27, 20, 4);
    int row = 0;
      byte nok[] = {
        B00000,
        B00000,
        B00000,
        B01110,
        B00000,
        B11000,
        B01000,
        B10000,
      };


  //RTC-----------------------------------------------------
    RTC_DS3231 rtc;
    String monthArray[12] = { "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" };
    int lastMinute = 60;
    int todaysMonth = NULL;
    int lastSecond;


  //TEMPERATURE --------------------------------------------
    DHT11 dht11(2);

  //Expenditure --------------------------------------------
    //int eachDayThisMonthArray[31] = {};
    //int moneySpentEachDay[31] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
    int moneySpentEachDay[31] = { 198, 209, 669, 407, 240, 77, 92, 385, 1064, 437, 520, 8, 514, 594, 778, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
    //int moneySpentEachDay[31] = {};
    int daysInEachMonth[12] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
    int avgExpensesPerDay;
    int totalMoneyPerMonth = 8000;
    int moneyLeftModifyer;
    int moneySpentSoFar;
    int daysLeftThisMonth;
    int moneyLeftThisMonth;
    int moneyLeftPerDay;
  //MENU----------------------------------------------------
    int timeoutEndTime;
    int currentScreen;
    int currentCursor;
    int lastCursorPlacement;

//DESIGNATION OF VALUES-----------------------------------

void setup() {
  //DateTime now = rtc.now();
  // put your setup code here, to run once:
  Serial.begin(9600);
  Serial.flush();
  //initialize lcd screen
  lcd.init();
  // turn on the backlight
  lcd.backlight();
  lcd.createChar(0, nok);
  //IR controller settings--------------------------------------------------
    irController.begin();
  //RTC settings------------------------------------------------------------
    if (!rtc.begin()) {
      Serial.println(F("Couldn't find RTC"));
      Serial.flush();
      while (1) delay(10);
    }
    if (rtc.lostPower()) {
      Serial.println(F("RTC lost power, let's set the time!"));
      // When time needs to be set on a new device, or after a power loss, the
      // following line sets the RTC to the date & time this sketch was compiled
      // rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));
      // This line sets the RTC with an explicit date & time, for example to set
      // January 21, 2014 at 3am you would call:
      // rtc.adjust(DateTime(2014, 1, 21, 3, 0, 0));
    }
    DateTime now = rtc.now();
    todaysMonth = now.month();
  //Expenditure standard settings-------------------------------------------
   //totalMoneyPerMonth = 8000;
}
void loop() {
  DateTime now = rtc.now();
  char customKey = customKeypad.getKey();
  
  
  if (customKey) {
    //Serial.println(customKey);
    if (customKey == 'A') {
      currentScreen = 1;
      currentCursor = 1;
      mainMenu();
      //newMenu();
    }
  }

  if (moneyLeftPerDay == NULL) {
    //Serial.println("moneyLeftPerDay from loop is running");
    for (int i = 0; i < 30; i++) {
      //Adding the expenditure for today into the moneySpentForEachDay array --------------------
      int x = moneySpentEachDay[i];
      moneySpentSoFar = moneySpentSoFar + x;
      moneyLeftThisMonth = totalMoneyPerMonth - moneySpentSoFar;
    }
    calculateMoneyLeftPerDay(0,0,0);
  }

  if (lastMinute != now.minute()) {
    //Serial.println("lastMinute check from loop has activated");
    printTimeDate();
  }

  if (todaysMonth != now.month()) {
    //Serial.print(todaysMonth);
    //Serial.print("|");
    //Serial.print(now.month());
    for (int i = 0; i < 30; i++) {
      moneySpentEachDay[i] = 0;
    }
    todaysMonth = now.month();
  }
}

//MAINMENU SCRIPTS ---------------------------------------
  void mainMenu() {
    int timeoutEndTime = NULL;
    Serial.println(currentScreen);
    displayScreen(currentScreen);
    displayCursor(currentCursor, 0);

    //Set a Timeout time -----------------------------------
      DateTime now = rtc.now();
      int currentTime = now.second();
      timeoutEndTime = now.second() + 25; 
      if (timeoutEndTime >= 60) { //KEEP SECONDS BASE 6
            timeoutEndTime = timeoutEndTime - 60;
      }
    //END---------------------------------------------------

    //CONTROLLER LOOP---------------------------------------
      while (true) {
        DateTime now = rtc.now();
        char customKey = customKeypad.getKey();
        //DETECT CURSOR MOVEMENT, UP OR DOWN----------------------
          if(customKey){
                if(customKey == '1'){ //CURSOR MOVE UP
                  if(currentCursor >= 2 && currentCursor <= 3){ // IF PAGE ONE
                    currentCursor--;
                    //Serial.print("  up - ");
                    //Serial.print(currentCursor);
                    delay(200);
                  } 
                  else if(currentCursor >= 5 && currentCursor <= 6){ // IF PAGE TWO
                    currentCursor--;
                    //Serial.print("  up - ");
                    //Serial.print(currentCursor);
                    delay(200);
                  }
                  else if(currentCursor == 4){ // IF currentCursor == 4
                    currentCursor--;
                    displayScreen(1); //DISPLAY MENU-SCREEN-ONE-------------------------
                    //Serial.print("  up - ");
                    //Serial.print(currentCursor);
                    delay(200);
                  }
                }
                if(customKey == '7'){ //CURSOR MOVE DOWN
                  if(currentCursor >= 1 && currentCursor <= 2){ // IF PAGE ONE
                    currentCursor++;
                    //Serial.print("down - ");
                    //Serial.print(currentCursor);
                    delay(200);
                  }
                  else if(currentCursor >= 4 && currentCursor <= 5){ // IF PAGE TWO
                      currentCursor++;
                      //Serial.print("down - ");
                      //Serial.print(currentCursor);
                      delay(200);
                  }
                  else if(currentCursor == 3){ // IF currentCursor == 3
                    currentCursor++;
                    displayScreen(2); //DISPLAY MENU-SCREEN-TWO ------------------------
                    //Serial.print("down - ");
                    //Serial.print(currentCursor);
                    delay(200);
                  }
                }
                if (customKey == '4'){ //CURSOR SELECT OPTION
                  lcd.clear();
                  selectCursor(currentCursor);
                  delay(200);
                  return;
                  }
          }
              

        //MOVE VISUAL CURSOR ON LCD-------------------------------
          if(lastCursorPlacement != currentCursor){
            displayCursor(currentCursor, lastCursorPlacement);
          }

        //TIMEOUT SHOWSTOPPER------------------
          if(timeoutEndTime == now.second()){
            returnToMain();
            return;
          } 
          if(lastSecond != now.second()) { // SERIAL.PRINT timeoutEndTime INFO
            Serial.print(F("Menu timeout :"));
            Serial.print(timeoutEndTime);
            Serial.print(F(" | "));
            Serial.print(now.second());
            Serial.println(F(": currentSecond"));
            lastSecond = now.second();
          }
      }
    //END---------------------------------------------------
  }
  void displayScreen(int page){
    switch(page) {
      case 1:
        lcd.clear();
        lcd.setCursor(8,0);
        lcd.print("MENU");
        lcd.setCursor(1,1);
        lcd.print("Calculator");
        lcd.setCursor(1,2);
        lcd.print("Todays Expense");
        lcd.setCursor(1,3);
        lcd.print("Edit Prev. Expense");
        currentScreen = 1;
      break;
      case 2:
        lcd.clear();
        lcd.setCursor(8,0);
        lcd.print("MENU");
        lcd.setCursor(1,1);
        lcd.print("Reset expenses");
        lcd.setCursor(1,2);
        lcd.print("Review Date");
        lcd.setCursor(1,3);
        lcd.print("Settings");
        currentScreen = 2;
      break;
      default:
        Serial.print(F("ERROR displayScreen: COULD NOT ASSERTAIN SCREEN REFERANCE NUMBER! === "));
        Serial.print(page);
      break;
    }
  }
  void displayCursor(int now, int then){
    if(now > 3){
      now = now - 3;
    }
    if(then > 3){
      then = then - 3;
    }
    lcd.setCursor(0, then);
    lcd.print(" ");
    lcd.setCursor(0, now);
    lcd.print(">");
    lastCursorPlacement = currentCursor;
    return;
  }
  void selectCursor(int select){
    delay(200);
      switch (select) {
        case 1:
          calculator();
          //Serial.println("Choose Calculator");
          break;
        case 2:
          expenditure();
          //Serial.println("Choose Expenditure");
          break;
        case 3:
          editExpenses();
          break;
        case 4:
          resetArray();
          break;
        case 5:
          reviewDate();
          break;
        case 6:
          settingsMenu();
          break;
        default:
          Serial.print(F("ERROR selectCursor: COULD NOT ASSERTAIN SCREEN REFERANCE NUMBER! === "));
          Serial.println(select);
          break;
      }
  }

//MENU OPTIONS -------------------------------------------
  void calculator() {
    lcd.clear();
    lcd.setCursor(5, 0);
    lcd.print("Calculator");
    lcd.setCursor(0, 3);
    lcd.print("Return * / # Confirm");

    DateTime now = rtc.now();


    int numberOne = 0;
    int numberTwo = 0;
    int setCursorA = 0;
    int answerOne = 0;
    int answerTwo = 0;

    while (numberTwo == 0) {
      row = 0;
      lcd.setCursor(0, 2);
      while (numberOne == 0) {
        numberOne = GetNumber(row,2);
        if (numberOne == 9999) {
          returnToMain();
          return;
        } else {
          lcd.setCursor(0, 2);
          lcd.print(numberOne);
          lcd.print("+");
          setCursorA = row + 1;
        }
      }
      numberTwo = GetNumber(setCursorA,2);
      lcd.setCursor(setCursorA, 2);
      lcd.print(numberTwo);
      if (numberTwo == 'end') {
        returnToMain();
      }
    }


    lcd.print("=");
    delay(50);
    int SUM = numberOne + numberTwo;
    lcd.print(SUM);
    delay(1000);

    while (answerOne == 0) {
      lcd.setCursor(0, 1);
      lcd.print("      Finished?     ");
      lcd.setCursor(0, 3);
      lcd.print("    No * / # Yes    ");
      answerOne = confirmation();
    }
    switch (answerOne) {
      case '*':  //NO---------------
        lcd.clear();
        calculator();  //RIGHT HERE the idea is that you'd be able to input a new number and add it to the previous sum--------------
        break;
      case '#':  //YES.............
        lcd.setCursor(2, 1);
        lcd.print("Add to expenses?");
        while (answerTwo == 0) {
          answerTwo = confirmation();
          switch (answerTwo) {
            case '*':  //NOO-----------------
              returnToMain();
              return;
            case '#':
              //MAKE A SCRIPT TO GO HERE THAT ADDS THIS "SUM" VALUE TO THE DAILY EXPENSES--------------------
              // INT is called "SUM"---------
              calculateMoneyLeftPerDay(now.day(), SUM, 0);
              returnToMain();
              return;
          }
        }
      case 'D':
        returnToMain();
        break;
    }
  }
  void expenditure() {
    //char numbers = customKeypad.getKey();
    DateTime now = rtc.now();
    row = 2;
    int numberOne = NULL;
    int answerOne = NULL;
    int checkForError = NULL;
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Expenditure");
    lcd.setCursor(0, 1);
    lcd.print("Add todays expenses");
    lcd.setCursor(0, 2);
    lcd.print("->");

    while (checkForError == NULL) {
      while (answerOne == NULL) {
        while (numberOne == NULL) {
          lcd.setCursor(0, 3);
          lcd.print("Return * / # Confirm");
          numberOne = GetNumber(row,2);
          if (numberOne == 9999) {
            returnToMain();
            return;
          }
          lcd.setCursor(2, 2);
          lcd.print(numberOne);
        }
        lcd.setCursor(0, 1);
        lcd.print("  Is this correct?  ");
        lcd.setCursor(0, 3);
        lcd.print("    No * / # Yes    ");
        answerOne = confirmation();
        returnToMain();
        return;
      }
    while (answerOne == NULL) {
      answerOne = confirmation();
      switch (answerOne) {
        case '*':  //NO---------------
          lcd.clear();
          editExpenses();
          break;
        case '#':  //YES.............
          calculateMoneyLeftPerDay(now.day(), numberOne,0);
          returnToMain();
          break;
      }
    }

      if (checkForError == 1) {
        //Add numberOne to the daily expenses for today----------------------
        calculateMoneyLeftPerDay(now.day(), numberOne,0);
        returnToMain();
        return;
      } else {
        returnToMain();
        return;
      }
    }
  }
  void editExpenses() {
    int expense = NULL;
    int date = NULL;
    int numberOne;
    int setCursorA;
    int answerOne = NULL;
    char numbers = customKeypad.getKey();
    DateTime now = rtc.now();
    row = 2;
    lcd.clear();
    lcd.setCursor(3, 0);
    lcd.print("Edit Expenses!");
    lcd.setCursor(0, 1);
    lcd.print("Choose a date");
    lcd.setCursor(0, 2);
    lcd.print("->");
    lcd.setCursor(0, 3);
    lcd.print("Return * / # Confirm");

    while (expense == NULL) {
      while (date == NULL) {
        date = GetNumber(row,2);
        if (date == 9999) {
          returnToMain();
          return;
        }
        lcd.setCursor(0, 1);
        lcd.print("Input expense");
        lcd.setCursor(0, 2);
        lcd.print("->           ");
      }
      row = 2;
      expense = GetNumber(row,2);
    }
    delay(200);
    lcd.setCursor(0, 2);
    lcd.print("Add ");
    lcd.print(expense);
    lcd.write(byte(0));
    lcd.print(" to ");
    lcd.print(date);
    lcd.print(".");
    lcd.print(monthArray[now.month() - 1]);
    lcd.print("?");
    lcd.setCursor(0, 3);
    lcd.print("    No * / # Yes    ");

    while (answerOne == NULL) {
      answerOne = confirmation();
      switch (answerOne) {
        case '*':  //NO---------------
          lcd.clear();
          editExpenses();
          break;
        case '#':  //YES.............
          calculateMoneyLeftPerDay(date, 0, expense);
          returnToMain();
          break;
      }
    }
  }
  void resetArray() {
    for (int i; i < 31; i++) {
      moneySpentEachDay[i] = 0;
    }
    calculateMoneyLeftPerDay(0,0,0);
    returnToMain();
  }
  void reviewDate() {
    DateTime now = rtc.now();
    int exit = NULL;
    int date = NULL;
    row = 5;
    lcd.clear();
    lcd.setCursor(4, 0);
    lcd.print("Review Date");
    lcd.setCursor(0,3);
    lcd.print("Return * / # Confirm");
    lcd.setCursor(0,1);
    lcd.print("Date: ");

    while(exit == NULL){
      while(date == NULL){
        date = GetNumber(row,1) - 1;
        if (date == 9999) {
          returnToMain();
          return;
        }
        lcd.setCursor(0,1);
        lcd.print("On the ");
        lcd.print(date+1);
        lcd.print(".");
        lcd.print(monthArray[now.month()-1]);
        lcd.setCursor(0,2);
        lcd.print("You spent:");
        lcd.print(moneySpentEachDay[date]);
        lcd.write(byte(0));
        lcd.setCursor(0,3);
        lcd.print("Return * / # Repeat ");
      }
      exit = customKeypad.getKey();
        if (exit == '*') {
        returnToMain();
        return;
      } else if (exit == '#'){
        reviewDate();
      }
    }
  }
  void settingsMenu() { //THIS SHIET IS NOT DONE AT ALL LOL---------
    DateTime now = rtc.now();
    int exit = NULL;
    int newValue = NULL;
    row = 5;
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.print("Settings");
  }

//REGULARY USED FUNCTIONS --------------------------------
  void returnToMain() {
    //  Serial.println("returnToMain RUNNING");
    timeoutEndTime = 0;
    lcd.clear();
    printTimeDate();
    loop();
    return;
  }
  int GetNumber(int Row, int Coloum) {
    //Serial.println("GetNumber is RUNNING");
    int num = 0;
    int buttonPressed = NULL;
    char key = customKeypad.getKey();
    Key17 command = irController.getKey();

    while (key != '#' && command != Key17::KEY_SHARP) {
      if(key){
        switch (key) {
          case NO_KEY:
            break;
          case '0':
          case '1':
          case '2':
          case '3':
          case '4':
          case '5':
          case '6':
          case '7':
          case '8':
          case '9':
            lcd.setCursor(Row, Coloum);
            lcd.print(key);
            num = num * 10 + (key - '0');
            Row++;
            delay(200);
            break;
          case '*':
            num = 9999;
            delay(200);
            break;
        }
      }
      if(command != Key17::UNKNOWN){
        switch (command) {
          case Key17::KEY_0:
            buttonPressed = 0;
            break;
          case Key17::KEY_1:
            buttonPressed = 1;
            break;
          case Key17::KEY_2:
            buttonPressed = 2;
            break;
          case Key17::KEY_3:
            buttonPressed = 3;
            break;
          case Key17::KEY_4:
            buttonPressed = 4;
            break;
          case Key17::KEY_5:
            buttonPressed = 5;
            break;
          case Key17::KEY_6:
            buttonPressed = 6;
            break;
          case Key17::KEY_7:
            buttonPressed = 7;
            break;
          case Key17::KEY_8:
            buttonPressed = 8;
            break;
          case Key17::KEY_9:
            buttonPressed = 9;
            break;
          case Key17::KEY_STAR:
            num = 9999;
            break;
        }
        delay(200);
        if(buttonPressed != NULL){ //Checks if a Switch-case: has happened;
          buttonPressed = NULL;
            lcd.setCursor(Row, Coloum);
            lcd.print(buttonPressed);
            num = num * 10 + (buttonPressed - '0');
            Row++;
        }
      }

      if (num == 9999) {
        key = '#';
      } else {
        key = customKeypad.getKey();
      }
    }
    row = Row;
    return num;
  }
  int confirmation() {
    int num = 0;
    char key = customKeypad.getKey();
    DateTime now = rtc.now();
    int timeoutEndTime;
    if (now.second() <= 30) {
      timeoutEndTime = now.second() + 10;
    }
    if (now.second() > 30) {
      timeoutEndTime = now.second() + 10;
      if (timeoutEndTime >= 60) {
        timeoutEndTime = (now.second() - 60) + 10;
      }
    }
    while (timeoutEndTime != now.second()) {
      switch (key) {
        case '*':
          num = key;
          break;
        case '#':
          num = key;
          break;
      }
      return key;
    }
    return;
  }
  void calculateMoneyLeftPerDay(int date, int expense, int addition) {
    DateTime now = rtc.now();
    daysLeftThisMonth = daysInEachMonth[now.month() - 1] - now.day();
    avgExpensesPerDay = totalMoneyPerMonth / 31;
    moneySpentSoFar = 0;
    int todaysDate = date - 1;

    //Calculating the moneyLeftThisMonth-----------------------------------
      if (expense != 0) { //Adding the expenditure for today into the moneySpentForEachDay array
        moneySpentEachDay[todaysDate] = expense;
      }
    //Adding expens to pre-existing value-------------------
      if (addition != 0){
        int prev = moneySpentEachDay[todaysDate];
        moneySpentEachDay[todaysDate] = prev + addition;
      }
    //Counting up the money spent so far this month---------------------------------
    for (int i = 0; i < 31; i++) {
      moneySpentSoFar = (moneySpentSoFar + moneySpentEachDay[i]);
    }
    
    moneyLeftThisMonth = totalMoneyPerMonth - moneySpentSoFar;
    moneyLeftModifyer = moneyLeftThisMonth / daysLeftThisMonth;
    moneyLeftPerDay = avgExpensesPerDay + (moneyLeftModifyer - avgExpensesPerDay);
    spiritTrain(date);
    return;
  }
  void spiritTrain(int date) {  //BULK SERIAL.PRINT OUTPUTS
    DateTime now = rtc.now();
    //moneySpentSoFar = 0;
    int todaysDate = date - 1;
    for (int i = 0; i < 31; i++) {
      Serial.print(F("Date:"));
      if (i < 9) {
        Serial.print(F("  "));
        Serial.print(i + 1);
      } else {
        Serial.print(F(" "));
        Serial.print(i + 1);
      }
      Serial.print(F(" | "));
      Serial.print(F("Money spent:"));
      if (moneySpentEachDay[i] < 10) {
        Serial.print(F("    "));
        Serial.print(moneySpentEachDay[i]);
      } else if (moneySpentEachDay[i] < 100) {
        Serial.print(F("   "));
        Serial.print(moneySpentEachDay[i]);
      } else if (moneySpentEachDay[i] < 1000) {
        Serial.print(F("  "));
        Serial.print(moneySpentEachDay[i]);
      } else {
        Serial.print(F(" "));
        Serial.print(moneySpentEachDay[i]);
      }

      Serial.print(F(" | "));
      Serial.print(F("moneySpentSoFar : "));
      Serial.println(moneySpentSoFar);
    }

    Serial.println(F("---------STATS---------"));
    Serial.print(F("daysLeftThisMonth = "));
    Serial.println(daysLeftThisMonth);
    Serial.print(F("avgExpensesPerDay = "));
    Serial.println(avgExpensesPerDay);
    Serial.print(F("moneyLeftModifyer = "));
    Serial.println(moneyLeftModifyer);
    Serial.print(F("totalMoneyPerMonth = "));
    Serial.println(totalMoneyPerMonth);
    Serial.print(F("moneySpentSoFar = "));
    Serial.println(moneySpentSoFar);
    Serial.print(F("moneyLeftThisMonth = "));
    Serial.println(moneyLeftThisMonth);
    Serial.print(F("moneyLeftPerDay = "));
    Serial.println(moneyLeftPerDay);
    Serial.println(F("---------------------"));
    return;
  }
  void printTimeDate() {
    DateTime now = rtc.now();
    int temperature = dht11.readTemperature();

    lcd.clear();
    lcd.setCursor(0, 0);
    if (now.day() < 10) {
      lcd.print("0");
      lcd.print(now.day());
    } else {
      lcd.print(now.day());
    }
    lcd.print(".");
    lcd.print(monthArray[now.month() - 1]);
    lcd.print(".");
    lcd.print(now.year());
    lcd.setCursor(15, 0);

    if (now.hour() < 10) {
      lcd.print("0");
      lcd.print(now.hour());
    } else {
      lcd.print(now.hour());
    }
    lcd.print(":");
    if (now.minute() < 10) {
      lcd.print("0");
      lcd.print(now.minute());
    } else {
      lcd.print(now.minute());
    }

    lcd.setCursor(14, 1);
    lcd.print(temperature, 1);
    lcd.print(char(223));
    lcd.print("C");

    lcd.setCursor(0, 3);
    lcd.print("Money p/Day = ");
    lcd.print(moneyLeftPerDay);
    lcd.write(byte(0));

    lastMinute = now.minute();
  }

LCD libraries generally allocate dynamic memory to create a buffer for the display.

Perhaps your system was already close to the RAM limits because of this and the IR controller pushed it over the edge. What Arduino are you using?

An Arduino UNO, this is what the Arduino IDE is telling me.

If running out of RAM is indeed your problem, why not use the F() macro to reduce your RAM usage?

From the PROGMEM reference page:

The F() macro

When an instruction like :

Serial.print("Write something on  the Serial Monitor");

is used, the string to be printed is normally saved in RAM. If your sketch prints a lot of stuff on the Serial Monitor, you can easily fill the RAM. This can be avoided by not loading strings from the FLASH memory space until they are needed. You can easily indicate that the string is not to be copied to RAM at start up using the syntax:

Serial.print(F("Write something on the Serial Monitor that is stored in FLASH"));

Where ever i have a Serial.print("something"), i have replaced it with the F() macro you speak of. My code fails to compile if i try to use that macro on something that issnt a sting.

You haven't done that to any of the lcd.print type statements.

1 Like

I did now know i could do that, i just went over my code and used the F() macro on every lcd.print("string"); line.
That fixed it for me so far, my lcd runs again.
My deployment tells me im still using 72% of dynamic memory, which worries me.
But for now it does work.
For referance im using 66% of storage space and 72% of dynamic memory.
considering that dynamic memory only is only 2k bytes, there should be something in my code that eats more than it probably should. Do you see anything else?

#include <LiquidCrystal_I2C.h>
#include <Keypad.h>
#include <RTClib.h>
#include <DHT11.h>
#include <DIYables_IRcontroller.h>

//DESIGNATION OF VALUES-----------------------------------
  //KEYPAD--------------------------------------------------
    const byte ROWS = 4;  //four rows
    const byte COLS = 4;  //four columns
    char hexaKeys[COLS][ROWS] = {
      { '1', '4', '7', '*' },
      { '2', '5', '8', '0' },
      { '3', '6', '9', '#' },
      { 'A', 'B', 'C', 'D' }
    };
    byte rowPins[ROWS] = { 7, 6, 5, 4 };    //connect to the row pinouts of the keypad
    byte colPins[COLS] = { 11, 10, 9, 8 };  //connect to the column pinouts of the keypad
    Keypad customKeypad = Keypad(makeKeymap(hexaKeys), rowPins, colPins, ROWS, COLS);

  //IR CONTROLLER-------------------------------------------
    #define IR_RECEIVER_PIN 3 // connect the IR Receiver to pin 3
    DIYables_IRcontroller_17 irController(IR_RECEIVER_PIN, 200); //debounce time is 200ms
  //LCD-----------------------------------------------------
    LiquidCrystal_I2C lcd(0x27, 20, 4);
    int row = 0;
      byte nok[] = {
        B00000,
        B00000,
        B00000,
        B01110,
        B00000,
        B11000,
        B01000,
        B10000,
      };


  //RTC-----------------------------------------------------
    RTC_DS3231 rtc;
    String monthArray[12] = { "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" };
    int lastMinute = 60;
    int todaysMonth = NULL;
    int lastSecond;


  //TEMPERATURE --------------------------------------------
    DHT11 dht11(2);

  //Expenditure --------------------------------------------
    //int eachDayThisMonthArray[31] = {};
    //int moneySpentEachDay[31] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
    int moneySpentEachDay[31] = { 198, 209, 669, 407, 240, 77, 92, 385, 1064, 437, 520, 8, 514, 594, 778, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
    //int moneySpentEachDay[31] = {};
    int daysInEachMonth[12] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 };
    int avgExpensesPerDay;
    int totalMoneyPerMonth = 8000;
    int moneyLeftModifyer;
    int moneySpentSoFar;
    int daysLeftThisMonth;
    int moneyLeftThisMonth;
    int moneyLeftPerDay;
  //MENU----------------------------------------------------
    int timeoutEndTime;
    int currentScreen;
    int currentCursor;
    int lastCursorPlacement;

//DESIGNATION OF VALUES-----------------------------------

void setup() {
  //DateTime now = rtc.now();
  // put your setup code here, to run once:
  Serial.begin(9600);
  Serial.flush();
  //initialize lcd screen
  lcd.init();
  // turn on the backlight
  lcd.backlight();
  lcd.createChar(0, nok);
  //IR controller settings--------------------------------------------------
    irController.begin();
  //RTC settings------------------------------------------------------------
    if (!rtc.begin()) {
      Serial.println(F("Couldn't find RTC"));
      Serial.flush();
      while (1) delay(10);
    }
    if (rtc.lostPower()) {
      Serial.println(F("RTC lost power, let's set the time!"));
      // When time needs to be set on a new device, or after a power loss, the
      // following line sets the RTC to the date & time this sketch was compiled
      // rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));
      // This line sets the RTC with an explicit date & time, for example to set
      // January 21, 2014 at 3am you would call:
      // rtc.adjust(DateTime(2014, 1, 21, 3, 0, 0));
    }
    DateTime now = rtc.now();
    todaysMonth = now.month();
  //Expenditure standard settings-------------------------------------------
   //totalMoneyPerMonth = 8000;
}
void loop() {
  DateTime now = rtc.now();
  char customKey = customKeypad.getKey();
  
  
  if (customKey) {
    //Serial.println(customKey);
    if (customKey == 'A') {
      currentScreen = 1;
      currentCursor = 1;
      mainMenu();
      //newMenu();
    }
  }

  if (moneyLeftPerDay == NULL) {
    //Serial.println("moneyLeftPerDay from loop is running");
    for (int i = 0; i < 30; i++) {
      //Adding the expenditure for today into the moneySpentForEachDay array --------------------
      int x = moneySpentEachDay[i];
      moneySpentSoFar = moneySpentSoFar + x;
      moneyLeftThisMonth = totalMoneyPerMonth - moneySpentSoFar;
    }
    calculateMoneyLeftPerDay(0,0,0);
  }

  if (lastMinute != now.minute()) {
    //Serial.println("lastMinute check from loop has activated");
    printTimeDate();
  }

  if (todaysMonth != now.month()) {
    //Serial.print(todaysMonth);
    //Serial.print("|");
    //Serial.print(now.month());
    for (int i = 0; i < 30; i++) {
      moneySpentEachDay[i] = 0;
    }
    todaysMonth = now.month();
  }
}

//MAINMENU SCRIPTS ---------------------------------------
  void mainMenu() {
    int timeoutEndTime = NULL;
    Serial.println(currentScreen);
    displayScreen(currentScreen);
    displayCursor(currentCursor, 0);

    //Set a Timeout time -----------------------------------
      DateTime now = rtc.now();
      int currentTime = now.second();
      timeoutEndTime = now.second() + 25; 
      if (timeoutEndTime >= 60) { //KEEP SECONDS BASE 6
            timeoutEndTime = timeoutEndTime - 60;
      }
    //END---------------------------------------------------

    //CONTROLLER LOOP---------------------------------------
      while (true) {
        DateTime now = rtc.now();
        char customKey = customKeypad.getKey();
        //DETECT CURSOR MOVEMENT, UP OR DOWN----------------------
          if(customKey){
                if(customKey == '1'){ //CURSOR MOVE UP
                  if(currentCursor >= 2 && currentCursor <= 3){ // IF PAGE ONE
                    currentCursor--;
                    //Serial.print("  up - ");
                    //Serial.print(currentCursor);
                    delay(200);
                  } 
                  else if(currentCursor >= 5 && currentCursor <= 6){ // IF PAGE TWO
                    currentCursor--;
                    //Serial.print("  up - ");
                    //Serial.print(currentCursor);
                    delay(200);
                  }
                  else if(currentCursor == 4){ // IF currentCursor == 4
                    currentCursor--;
                    displayScreen(1); //DISPLAY MENU-SCREEN-ONE-------------------------
                    //Serial.print("  up - ");
                    //Serial.print(currentCursor);
                    delay(200);
                  }
                }
                if(customKey == '7'){ //CURSOR MOVE DOWN
                  if(currentCursor >= 1 && currentCursor <= 2){ // IF PAGE ONE
                    currentCursor++;
                    //Serial.print("down - ");
                    //Serial.print(currentCursor);
                    delay(200);
                  }
                  else if(currentCursor >= 4 && currentCursor <= 5){ // IF PAGE TWO
                      currentCursor++;
                      //Serial.print("down - ");
                      //Serial.print(currentCursor);
                      delay(200);
                  }
                  else if(currentCursor == 3){ // IF currentCursor == 3
                    currentCursor++;
                    displayScreen(2); //DISPLAY MENU-SCREEN-TWO ------------------------
                    //Serial.print("down - ");
                    //Serial.print(currentCursor);
                    delay(200);
                  }
                }
                if (customKey == '4'){ //CURSOR SELECT OPTION
                  lcd.clear();
                  selectCursor(currentCursor);
                  delay(200);
                  return;
                  }
          }
              

        //MOVE VISUAL CURSOR ON LCD-------------------------------
          if(lastCursorPlacement != currentCursor){
            displayCursor(currentCursor, lastCursorPlacement);
          }

        //TIMEOUT SHOWSTOPPER------------------
          if(timeoutEndTime == now.second()){
            returnToMain();
            return;
          } 
          if(lastSecond != now.second()) { // SERIAL.PRINT timeoutEndTime INFO
            Serial.print(F("Menu timeout :"));
            Serial.print(timeoutEndTime);
            Serial.print(F(" | "));
            Serial.print(now.second());
            Serial.println(F(": currentSecond"));
            lastSecond = now.second();
          }
      }
    //END---------------------------------------------------
  }
  void displayScreen(int page){
    switch(page) {
      case 1:
        lcd.clear();
        lcd.setCursor(8,0);
        lcd.print(F("MENU"));
        lcd.setCursor(1,1);
        lcd.print(F("Calculator"));
        lcd.setCursor(1,2);
        lcd.print(F("Todays Expense"));
        lcd.setCursor(1,3);
        lcd.print(F("Edit Prev. Expense"));
        currentScreen = 1;
      break;
      case 2:
        lcd.clear();
        lcd.setCursor(8,0);
        lcd.print(F("MENU"));
        lcd.setCursor(1,1);
        lcd.print(F("Reset expenses"));
        lcd.setCursor(1,2);
        lcd.print(F("Review Date"));
        lcd.setCursor(1,3);
        lcd.print(F("Settings"));
        currentScreen = 2;
      break;
      default:
        Serial.print(F("ERROR displayScreen: COULD NOT ASSERTAIN SCREEN REFERANCE NUMBER! === "));
        Serial.print(page);
      break;
    }
  }
  void displayCursor(int now, int then){
    if(now > 3){
      now = now - 3;
    }
    if(then > 3){
      then = then - 3;
    }
    lcd.setCursor(0, then);
    lcd.print(F(" "));
    lcd.setCursor(0, now);
    lcd.print(F(">"));
    lastCursorPlacement = currentCursor;
    return;
  }
  void selectCursor(int select){
    delay(200);
      switch (select) {
        case 1:
          calculator();
          //Serial.println("Choose Calculator");
          break;
        case 2:
          expenditure();
          //Serial.println("Choose Expenditure");
          break;
        case 3:
          editExpenses();
          break;
        case 4:
          resetArray();
          break;
        case 5:
          reviewDate();
          break;
        case 6:
          settingsMenu();
          break;
        default:
          Serial.print(F("ERROR selectCursor: COULD NOT ASSERTAIN SCREEN REFERANCE NUMBER! === "));
          Serial.println(select);
          break;
      }
  }

//MENU OPTIONS -------------------------------------------
  void calculator() {
    lcd.clear();
    lcd.setCursor(5, 0);
    lcd.print(F("Calculator"));
    lcd.setCursor(0, 3);
    lcd.print(F("Return * / # Confirm"));

    DateTime now = rtc.now();


    int numberOne = 0;
    int numberTwo = 0;
    int setCursorA = 0;
    int answerOne = 0;
    int answerTwo = 0;

    while (numberTwo == 0) {
      row = 0;
      lcd.setCursor(0, 2);
      while (numberOne == 0) {
        numberOne = GetNumber(row,2);
        if (numberOne == 9999) {
          returnToMain();
          return;
        } else {
          lcd.setCursor(0, 2);
          lcd.print(numberOne);
          lcd.print(F("+"));
          setCursorA = row + 1;
        }
      }
      numberTwo = GetNumber(setCursorA,2);
      lcd.setCursor(setCursorA, 2);
      lcd.print(numberTwo);
      if (numberTwo == 'end') {
        returnToMain();
      }
    }


    lcd.print(F("="));
    delay(50);
    int SUM = numberOne + numberTwo;
    lcd.print(SUM);
    delay(1000);

    while (answerOne == 0) {
      lcd.setCursor(0, 1);
      lcd.print(F("      Finished?     "));
      lcd.setCursor(0, 3);
      lcd.print(F("    No * / # Yes    "));
      answerOne = confirmation();
    }
    switch (answerOne) {
      case '*':  //NO---------------
        lcd.clear();
        calculator();  //RIGHT HERE the idea is that you'd be able to input a new number and add it to the previous sum--------------
        break;
      case '#':  //YES.............
        lcd.setCursor(2, 1);
        lcd.print(F("Add to expenses?"));
        while (answerTwo == 0) {
          answerTwo = confirmation();
          switch (answerTwo) {
            case '*':  //NOO-----------------
              returnToMain();
              return;
            case '#':
              //MAKE A SCRIPT TO GO HERE THAT ADDS THIS "SUM" VALUE TO THE DAILY EXPENSES--------------------
              // INT is called "SUM"---------
              calculateMoneyLeftPerDay(now.day(), SUM, 0);
              returnToMain();
              return;
          }
        }
      case 'D':
        returnToMain();
        break;
    }
  }
  void expenditure() {
    //char numbers = customKeypad.getKey();
    DateTime now = rtc.now();
    row = 2;
    int numberOne = NULL;
    int answerOne = NULL;
    int checkForError = NULL;
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print(F("Expenditure"));
    lcd.setCursor(0, 1);
    lcd.print(F("Add todays expenses"));
    lcd.setCursor(0, 2);
    lcd.print(F("->"));

    while (checkForError == NULL) {
      while (answerOne == NULL) {
        while (numberOne == NULL) {
          lcd.setCursor(0, 3);
          lcd.print(F("Return * / # Confirm"));
          numberOne = GetNumber(row,2);
          if (numberOne == 9999) {
            returnToMain();
            return;
          }
          lcd.setCursor(2, 2);
          lcd.print(numberOne);
        }
        lcd.setCursor(0, 1);
        lcd.print(F("  Is this correct?  "));
        lcd.setCursor(0, 3);
        lcd.print(F("    No * / # Yes    "));
        answerOne = confirmation();
        returnToMain();
        return;
      }
    while (answerOne == NULL) {
      answerOne = confirmation();
      switch (answerOne) {
        case '*':  //NO---------------
          lcd.clear();
          editExpenses();
          break;
        case '#':  //YES.............
          calculateMoneyLeftPerDay(now.day(), numberOne,0);
          returnToMain();
          break;
      }
    }

      if (checkForError == 1) {
        //Add numberOne to the daily expenses for today----------------------
        calculateMoneyLeftPerDay(now.day(), numberOne,0);
        returnToMain();
        return;
      } else {
        returnToMain();
        return;
      }
    }
  }
  void editExpenses() {
    int expense = NULL;
    int date = NULL;
    int numberOne;
    int setCursorA;
    int answerOne = NULL;
    char numbers = customKeypad.getKey();
    DateTime now = rtc.now();
    row = 2;
    lcd.clear();
    lcd.setCursor(3, 0);
    lcd.print(F("Edit Expenses!"));
    lcd.setCursor(0, 1);
    lcd.print(F("Choose a date"));
    lcd.setCursor(0, 2);
    lcd.print(F("->"));
    lcd.setCursor(0, 3);
    lcd.print(F("Return * / # Confirm"));

    while (expense == NULL) {
      while (date == NULL) {
        date = GetNumber(row,2);
        if (date == 9999) {
          returnToMain();
          return;
        }
        lcd.setCursor(0, 1);
        lcd.print(F("Input expense"));
        lcd.setCursor(0, 2);
        lcd.print(F("->           "));
      }
      row = 2;
      expense = GetNumber(row,2);
    }
    delay(200);
    lcd.setCursor(0, 2);
    lcd.print(F("Add "));
    lcd.print(expense);
    lcd.write(byte(0));
    lcd.print(F(" to "));
    lcd.print(date);
    lcd.print(F("."));
    lcd.print(monthArray[now.month() - 1]);
    lcd.print(F("?"));
    lcd.setCursor(0, 3);
    lcd.print(F("    No * / # Yes    "));

    while (answerOne == NULL) {
      answerOne = confirmation();
      switch (answerOne) {
        case '*':  //NO---------------
          lcd.clear();
          editExpenses();
          break;
        case '#':  //YES.............
          calculateMoneyLeftPerDay(date, 0, expense);
          returnToMain();
          break;
      }
    }
  }
  void resetArray() {
    for (int i; i < 31; i++) {
      moneySpentEachDay[i] = 0;
    }
    calculateMoneyLeftPerDay(0,0,0);
    returnToMain();
  }
  void reviewDate() {
    DateTime now = rtc.now();
    int exit = NULL;
    int date = NULL;
    row = 5;
    lcd.clear();
    lcd.setCursor(4, 0);
    lcd.print(F("Review Date"));
    lcd.setCursor(0,3);
    lcd.print(F("Return * / # Confirm"));
    lcd.setCursor(0,1);
    lcd.print(F("Date: "));

    while(exit == NULL){
      while(date == NULL){
        date = GetNumber(row,1) - 1;
        if (date == 9999) {
          returnToMain();
          return;
        }
        lcd.setCursor(0,1);
        lcd.print(F("On the "));
        lcd.print(date+1);
        lcd.print(F("."));
        lcd.print(monthArray[now.month()-1]);
        lcd.setCursor(0,2);
        lcd.print(F("You spent:"));
        lcd.print(moneySpentEachDay[date]);
        lcd.write(byte(0));
        lcd.setCursor(0,3);
        lcd.print(F("Return * / # Repeat "));
      }
      exit = customKeypad.getKey();
        if (exit == '*') {
        returnToMain();
        return;
      } else if (exit == '#'){
        reviewDate();
      }
    }
  }
  void settingsMenu() { //THIS SHIET IS NOT DONE AT ALL LOL---------
    DateTime now = rtc.now();
    int exit = NULL;
    int newValue = NULL;
    row = 5;
    lcd.clear();
    lcd.setCursor(0,0);
    lcd.print(F("Settings"));
  }

//REGULARY USED FUNCTIONS --------------------------------
  void returnToMain() {
    //  Serial.println("returnToMain RUNNING");
    timeoutEndTime = 0;
    lcd.clear();
    printTimeDate();
    loop();
    return;
  }
  int GetNumber(int Row, int Coloum) {
    //Serial.println("GetNumber is RUNNING");
    int num = 0;
    int buttonPressed = NULL;
    char key = customKeypad.getKey();
    Key17 command = irController.getKey();

    while (key != '#' && command != Key17::KEY_SHARP) {
      if(key){
        switch (key) {
          case NO_KEY:
            break;
          case '0':
          case '1':
          case '2':
          case '3':
          case '4':
          case '5':
          case '6':
          case '7':
          case '8':
          case '9':
            lcd.setCursor(Row, Coloum);
            lcd.print(key);
            num = num * 10 + (key - '0');
            Row++;
            delay(200);
            break;
          case '*':
            num = 9999;
            delay(200);
            break;
        }
      }
      if(command != Key17::UNKNOWN){
        switch (command) {
          case Key17::KEY_0:
            buttonPressed = 0;
            break;
          case Key17::KEY_1:
            buttonPressed = 1;
            break;
          case Key17::KEY_2:
            buttonPressed = 2;
            break;
          case Key17::KEY_3:
            buttonPressed = 3;
            break;
          case Key17::KEY_4:
            buttonPressed = 4;
            break;
          case Key17::KEY_5:
            buttonPressed = 5;
            break;
          case Key17::KEY_6:
            buttonPressed = 6;
            break;
          case Key17::KEY_7:
            buttonPressed = 7;
            break;
          case Key17::KEY_8:
            buttonPressed = 8;
            break;
          case Key17::KEY_9:
            buttonPressed = 9;
            break;
          case Key17::KEY_STAR:
            num = 9999;
            break;
        }
        delay(200);
        if(buttonPressed != NULL){ //Checks if a Switch-case: has happened;
          buttonPressed = NULL;
            lcd.setCursor(Row, Coloum);
            lcd.print(buttonPressed);
            num = num * 10 + (buttonPressed - '0');
            Row++;
        }
      }

      if (num == 9999) {
        key = '#';
      } else {
        key = customKeypad.getKey();
      }
    }
    row = Row;
    return num;
  }
  int confirmation() {
    int num = 0;
    char key = customKeypad.getKey();
    DateTime now = rtc.now();
    int timeoutEndTime;
    if (now.second() <= 30) {
      timeoutEndTime = now.second() + 10;
    }
    if (now.second() > 30) {
      timeoutEndTime = now.second() + 10;
      if (timeoutEndTime >= 60) {
        timeoutEndTime = (now.second() - 60) + 10;
      }
    }
    while (timeoutEndTime != now.second()) {
      switch (key) {
        case '*':
          num = key;
          break;
        case '#':
          num = key;
          break;
      }
      return key;
    }
    return;
  }
  void calculateMoneyLeftPerDay(int date, int expense, int addition) {
    DateTime now = rtc.now();
    daysLeftThisMonth = daysInEachMonth[now.month() - 1] - now.day();
    avgExpensesPerDay = totalMoneyPerMonth / 31;
    moneySpentSoFar = 0;
    int todaysDate = date - 1;

    //Calculating the moneyLeftThisMonth-----------------------------------
      if (expense != 0) { //Adding the expenditure for today into the moneySpentForEachDay array
        moneySpentEachDay[todaysDate] = expense;
      }
    //Adding expens to pre-existing value-------------------
      if (addition != 0){
        int prev = moneySpentEachDay[todaysDate];
        moneySpentEachDay[todaysDate] = prev + addition;
      }
    //Counting up the money spent so far this month---------------------------------
    for (int i = 0; i < 31; i++) {
      moneySpentSoFar = (moneySpentSoFar + moneySpentEachDay[i]);
    }
    
    moneyLeftThisMonth = totalMoneyPerMonth - moneySpentSoFar;
    moneyLeftModifyer = moneyLeftThisMonth / daysLeftThisMonth;
    moneyLeftPerDay = avgExpensesPerDay + (moneyLeftModifyer - avgExpensesPerDay);
    spiritTrain(date);
    return;
  }
  void spiritTrain(int date) {  //BULK SERIAL.PRINT OUTPUTS
    DateTime now = rtc.now();
    //moneySpentSoFar = 0;
    int todaysDate = date - 1;
    for (int i = 0; i < 31; i++) {
      Serial.print(F("Date:"));
      if (i < 9) {
        Serial.print(F("  "));
        Serial.print(i + 1);
      } else {
        Serial.print(F(" "));
        Serial.print(i + 1);
      }
      Serial.print(F(" | "));
      Serial.print(F("Money spent:"));
      if (moneySpentEachDay[i] < 10) {
        Serial.print(F("    "));
        Serial.print(moneySpentEachDay[i]);
      } else if (moneySpentEachDay[i] < 100) {
        Serial.print(F("   "));
        Serial.print(moneySpentEachDay[i]);
      } else if (moneySpentEachDay[i] < 1000) {
        Serial.print(F("  "));
        Serial.print(moneySpentEachDay[i]);
      } else {
        Serial.print(F(" "));
        Serial.print(moneySpentEachDay[i]);
      }

      Serial.print(F(" | "));
      Serial.print(F("moneySpentSoFar : "));
      Serial.println(moneySpentSoFar);
    }

    Serial.println(F("---------STATS---------"));
    Serial.print(F("daysLeftThisMonth = "));
    Serial.println(daysLeftThisMonth);
    Serial.print(F("avgExpensesPerDay = "));
    Serial.println(avgExpensesPerDay);
    Serial.print(F("moneyLeftModifyer = "));
    Serial.println(moneyLeftModifyer);
    Serial.print(F("totalMoneyPerMonth = "));
    Serial.println(totalMoneyPerMonth);
    Serial.print(F("moneySpentSoFar = "));
    Serial.println(moneySpentSoFar);
    Serial.print(F("moneyLeftThisMonth = "));
    Serial.println(moneyLeftThisMonth);
    Serial.print(F("moneyLeftPerDay = "));
    Serial.println(moneyLeftPerDay);
    Serial.println(F("---------------------"));
    return;
  }
  void printTimeDate() {
    DateTime now = rtc.now();
    int temperature = dht11.readTemperature();

    lcd.clear();
    lcd.setCursor(0, 0);
    if (now.day() < 10) {
      lcd.print(F("0"));
      lcd.print(now.day());
    } else {
      lcd.print(now.day());
    }
    lcd.print(F("."));
    lcd.print(monthArray[now.month() - 1]);
    lcd.print(F("."));
    lcd.print(now.year());
    lcd.setCursor(15, 0);

    if (now.hour() < 10) {
      lcd.print(F("0"));
      lcd.print(now.hour());
    } else {
      lcd.print(now.hour());
    }
    lcd.print(F(":"));
    if (now.minute() < 10) {
      lcd.print(F("0"));
      lcd.print(now.minute());
    } else {
      lcd.print(now.minute());
    }

    lcd.setCursor(14, 1);
    lcd.print(temperature, 1);
    lcd.print(char(223));
    lcd.print(F("C"));

    lcd.setCursor(0, 3);
    lcd.print(F("Money p/Day = "));
    lcd.print(moneyLeftPerDay);
    lcd.write(byte(0));

    lastMinute = now.minute();
  }

you can save a few bytes if you store these in progmem too


you don't need an int for the number of days. a byte would be enough ➜ save 12 bytes


you still have all the lcd.print without using the F() macro when printing text

Anything under 80% should be ok,…
More than that depends on your coding style and dynamic use of memory,

The stack and heap can use a lot of memory in complex programs - so 65% is my personal ‘max’ in almost every project
jeff.

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.